diff --git a/Documentation/sphinx/parse-headers.pl b/Documentation/sphinx/parse-headers.pl index c518050ffc3fb..0dcf369ab9040 100755 --- a/Documentation/sphinx/parse-headers.pl +++ b/Documentation/sphinx/parse-headers.pl @@ -1,4 +1,4 @@ -#!/usr/bin/perl +#!/usr/bin/env perl use strict; use Text::Tabs; use Getopt::Long; diff --git a/Documentation/target/tcm_mod_builder.py b/Documentation/target/tcm_mod_builder.py index 94bf6944bb1e4..7e79ff6b09e0e 100755 --- a/Documentation/target/tcm_mod_builder.py +++ b/Documentation/target/tcm_mod_builder.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/env python # The TCM v4 multi-protocol fabric module generation script for drivers/target/$NEW_MOD # # Copyright (c) 2010 Rising Tide Systems diff --git a/Documentation/trace/postprocess/decode_msr.py b/Documentation/trace/postprocess/decode_msr.py index 0ab40e0db5809..aa9cc7abd5c2b 100644 --- a/Documentation/trace/postprocess/decode_msr.py +++ b/Documentation/trace/postprocess/decode_msr.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/env python # add symbolic names to read_msr / write_msr in trace # decode_msr msr-index.h < trace import sys diff --git a/Documentation/trace/postprocess/trace-pagealloc-postprocess.pl b/Documentation/trace/postprocess/trace-pagealloc-postprocess.pl index 0a120aae33ce5..b9b7d80c2f9d2 100644 --- a/Documentation/trace/postprocess/trace-pagealloc-postprocess.pl +++ b/Documentation/trace/postprocess/trace-pagealloc-postprocess.pl @@ -1,4 +1,4 @@ -#!/usr/bin/perl +#!/usr/bin/env perl # This is a POC (proof of concept or piece of crap, take your pick) for reading the # text representation of trace output related to page allocation. It makes an attempt # to extract some high-level information on what is going on. The accuracy of the parser diff --git a/Documentation/trace/postprocess/trace-vmscan-postprocess.pl b/Documentation/trace/postprocess/trace-vmscan-postprocess.pl index 66bfd8396877f..9efcf5ed8cb50 100644 --- a/Documentation/trace/postprocess/trace-vmscan-postprocess.pl +++ b/Documentation/trace/postprocess/trace-vmscan-postprocess.pl @@ -1,4 +1,4 @@ -#!/usr/bin/perl +#!/usr/bin/env perl # This is a POC for reading the text representation of trace output related to # page reclaim. It makes an attempt to extract some high-level information on # what is going on. The accuracy of the parser may vary diff --git a/Makefile b/Makefile index c813c3bb74055..586a2d128ffb3 100644 --- a/Makefile +++ b/Makefile @@ -1,7 +1,7 @@ # SPDX-License-Identifier: GPL-2.0 VERSION = 4 PATCHLEVEL = 19 -SUBLEVEL = 190 +SUBLEVEL = 191 EXTRAVERSION = NAME = "People's Front" diff --git a/arch/arc/kernel/entry.S b/arch/arc/kernel/entry.S index 85d9ea4a0accc..37ad245cf9899 100644 --- a/arch/arc/kernel/entry.S +++ b/arch/arc/kernel/entry.S @@ -169,7 +169,7 @@ tracesys: ; Do the Sys Call as we normally would. ; Validate the Sys Call number - cmp r8, NR_syscalls + cmp r8, NR_syscalls - 1 mov.hi r0, -ENOSYS bhi tracesys_exit @@ -252,7 +252,7 @@ ENTRY(EV_Trap) ;============ Normal syscall case ; syscall num shd not exceed the total system calls avail - cmp r8, NR_syscalls + cmp r8, NR_syscalls - 1 mov.hi r0, -ENOSYS bhi .Lret_from_system_call diff --git a/arch/arm/boot/compressed/Makefile b/arch/arm/boot/compressed/Makefile index c762004572eff..ec2327a3796d5 100644 --- a/arch/arm/boot/compressed/Makefile +++ b/arch/arm/boot/compressed/Makefile @@ -121,8 +121,8 @@ asflags-y := -DZIMAGE # Supply kernel BSS size to the decompressor via a linker symbol. KBSS_SZ = $(shell echo $$(($$($(NM) $(obj)/../../../../vmlinux | \ - sed -n -e 's/^\([^ ]*\) [AB] __bss_start$$/-0x\1/p' \ - -e 's/^\([^ ]*\) [AB] __bss_stop$$/+0x\1/p') )) ) + sed -n -e 's/^\([^ ]*\) [ABD] __bss_start$$/-0x\1/p' \ + -e 's/^\([^ ]*\) [ABD] __bss_stop$$/+0x\1/p') )) ) LDFLAGS_vmlinux = --defsym _kernel_bss_size=$(KBSS_SZ) # Supply ZRELADDR to the decompressor via a linker symbol. ifneq ($(CONFIG_AUTO_ZRELADDR),y) diff --git a/arch/arm/boot/dts/exynos4412-midas.dtsi b/arch/arm/boot/dts/exynos4412-midas.dtsi index c0476c2909774..60fbad25b5f26 100644 --- a/arch/arm/boot/dts/exynos4412-midas.dtsi +++ b/arch/arm/boot/dts/exynos4412-midas.dtsi @@ -139,7 +139,7 @@ max77693@66 { compatible = "maxim,max77693"; interrupt-parent = <&gpx1>; - interrupts = <5 IRQ_TYPE_EDGE_FALLING>; + interrupts = <5 IRQ_TYPE_LEVEL_LOW>; pinctrl-names = "default"; pinctrl-0 = <&max77693_irq>; reg = <0x66>; @@ -187,7 +187,7 @@ max77693-fuel-gauge@36 { compatible = "maxim,max17047"; interrupt-parent = <&gpx2>; - interrupts = <3 IRQ_TYPE_EDGE_FALLING>; + interrupts = <3 IRQ_TYPE_LEVEL_LOW>; pinctrl-names = "default"; pinctrl-0 = <&max77693_fuel_irq>; reg = <0x36>; @@ -579,7 +579,7 @@ max77686: max77686_pmic@9 { compatible = "maxim,max77686"; interrupt-parent = <&gpx0>; - interrupts = <7 IRQ_TYPE_NONE>; + interrupts = <7 IRQ_TYPE_LEVEL_LOW>; pinctrl-0 = <&max77686_irq>; pinctrl-names = "default"; reg = <0x09>; diff --git a/arch/arm/boot/dts/exynos4412-odroid-common.dtsi b/arch/arm/boot/dts/exynos4412-odroid-common.dtsi index 00820d2397537..dbca8eeefae13 100644 --- a/arch/arm/boot/dts/exynos4412-odroid-common.dtsi +++ b/arch/arm/boot/dts/exynos4412-odroid-common.dtsi @@ -265,7 +265,7 @@ max77686: pmic@9 { compatible = "maxim,max77686"; interrupt-parent = <&gpx3>; - interrupts = <2 IRQ_TYPE_NONE>; + interrupts = <2 IRQ_TYPE_LEVEL_LOW>; pinctrl-names = "default"; pinctrl-0 = <&max77686_irq>; reg = <0x09>; diff --git a/arch/arm/boot/dts/exynos5250-smdk5250.dts b/arch/arm/boot/dts/exynos5250-smdk5250.dts index d5e66189ed2a0..594b246afbedc 100644 --- a/arch/arm/boot/dts/exynos5250-smdk5250.dts +++ b/arch/arm/boot/dts/exynos5250-smdk5250.dts @@ -132,7 +132,7 @@ compatible = "maxim,max77686"; reg = <0x09>; interrupt-parent = <&gpx3>; - interrupts = <2 IRQ_TYPE_NONE>; + interrupts = <2 IRQ_TYPE_LEVEL_LOW>; pinctrl-names = "default"; pinctrl-0 = <&max77686_irq>; wakeup-source; diff --git a/arch/arm/boot/dts/exynos5250-snow-common.dtsi b/arch/arm/boot/dts/exynos5250-snow-common.dtsi index fd9226d3b207e..3981acb00b5e4 100644 --- a/arch/arm/boot/dts/exynos5250-snow-common.dtsi +++ b/arch/arm/boot/dts/exynos5250-snow-common.dtsi @@ -292,7 +292,7 @@ max77686: max77686@9 { compatible = "maxim,max77686"; interrupt-parent = <&gpx3>; - interrupts = <2 IRQ_TYPE_NONE>; + interrupts = <2 IRQ_TYPE_LEVEL_LOW>; pinctrl-names = "default"; pinctrl-0 = <&max77686_irq>; wakeup-source; diff --git a/arch/arm/boot/dts/uniphier-pxs2.dtsi b/arch/arm/boot/dts/uniphier-pxs2.dtsi index e2d1a22c5950d..d8a32104aad0b 100644 --- a/arch/arm/boot/dts/uniphier-pxs2.dtsi +++ b/arch/arm/boot/dts/uniphier-pxs2.dtsi @@ -513,7 +513,7 @@ clocks = <&sys_clk 6>; reset-names = "ether"; resets = <&sys_rst 6>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; local-mac-address = [00 00 00 00 00 00]; socionext,syscon-phy-mode = <&soc_glue 0>; diff --git a/arch/arm/include/asm/kvm_host.h b/arch/arm/include/asm/kvm_host.h index 471859cbfe0bb..ae073fceb3f05 100644 --- a/arch/arm/include/asm/kvm_host.h +++ b/arch/arm/include/asm/kvm_host.h @@ -303,6 +303,7 @@ static inline void kvm_arch_sched_in(struct kvm_vcpu *vcpu, int cpu) {} static inline void kvm_arch_vcpu_block_finish(struct kvm_vcpu *vcpu) {} static inline void kvm_arm_init_debug(void) {} +static inline void kvm_arm_vcpu_init_debug(struct kvm_vcpu *vcpu) {} static inline void kvm_arm_setup_debug(struct kvm_vcpu *vcpu) {} static inline void kvm_arm_clear_debug(struct kvm_vcpu *vcpu) {} static inline void kvm_arm_reset_debug_ptr(struct kvm_vcpu *vcpu) {} diff --git a/arch/arm/kernel/asm-offsets.c b/arch/arm/kernel/asm-offsets.c index ae85f67a63520..40afe953a0e2d 100644 --- a/arch/arm/kernel/asm-offsets.c +++ b/arch/arm/kernel/asm-offsets.c @@ -30,6 +30,7 @@ #include #include #include +#include #include "signal.h" /* @@ -159,6 +160,8 @@ int main(void) DEFINE(SLEEP_SAVE_SP_PHYS, offsetof(struct sleep_save_sp, save_ptr_stash_phys)); DEFINE(SLEEP_SAVE_SP_VIRT, offsetof(struct sleep_save_sp, save_ptr_stash)); #endif + DEFINE(ARM_SMCCC_QUIRK_ID_OFFS, offsetof(struct arm_smccc_quirk, id)); + DEFINE(ARM_SMCCC_QUIRK_STATE_OFFS, offsetof(struct arm_smccc_quirk, state)); BLANK(); DEFINE(DMA_BIDIRECTIONAL, DMA_BIDIRECTIONAL); DEFINE(DMA_TO_DEVICE, DMA_TO_DEVICE); diff --git a/arch/arm/kernel/hw_breakpoint.c b/arch/arm/kernel/hw_breakpoint.c index 97fa9c1677576..2ee5b7f5e7ad0 100644 --- a/arch/arm/kernel/hw_breakpoint.c +++ b/arch/arm/kernel/hw_breakpoint.c @@ -891,7 +891,7 @@ static void breakpoint_handler(unsigned long unknown, struct pt_regs *regs) info->trigger = addr; pr_debug("breakpoint fired: address = 0x%x\n", addr); perf_bp_event(bp, regs); - if (!bp->overflow_handler) + if (is_default_overflow_handler(bp)) enable_single_step(bp, addr); goto unlock; } diff --git a/arch/arm/kernel/smccc-call.S b/arch/arm/kernel/smccc-call.S index e5d43066b8894..13d307cd364c5 100644 --- a/arch/arm/kernel/smccc-call.S +++ b/arch/arm/kernel/smccc-call.S @@ -12,7 +12,9 @@ * */ #include +#include +#include #include #include #include @@ -36,7 +38,14 @@ UNWIND( .fnstart) UNWIND( .save {r4-r7}) ldm r12, {r4-r7} \instr - pop {r4-r7} + ldr r4, [sp, #36] + cmp r4, #0 + beq 1f // No quirk structure + ldr r5, [r4, #ARM_SMCCC_QUIRK_ID_OFFS] + cmp r5, #ARM_SMCCC_QUIRK_QCOM_A6 + bne 1f // No quirk present + str r6, [r4, #ARM_SMCCC_QUIRK_STATE_OFFS] +1: pop {r4-r7} ldr r12, [sp, #(4 * 4)] stm r12, {r0-r3} bx lr diff --git a/arch/arm/kernel/suspend.c b/arch/arm/kernel/suspend.c index d08099269e35b..e126386fb78a8 100644 --- a/arch/arm/kernel/suspend.c +++ b/arch/arm/kernel/suspend.c @@ -1,4 +1,5 @@ // SPDX-License-Identifier: GPL-2.0 +#include #include #include #include @@ -26,6 +27,13 @@ int cpu_suspend(unsigned long arg, int (*fn)(unsigned long)) if (!idmap_pgd) return -EINVAL; + /* + * Function graph tracer state gets incosistent when the kernel + * calls functions that never return (aka suspend finishers) hence + * disable graph tracing during their execution. + */ + pause_graph_tracing(); + /* * Provide a temporary page table with an identity mapping for * the MMU-enable code, required for resuming. On successful @@ -33,6 +41,9 @@ int cpu_suspend(unsigned long arg, int (*fn)(unsigned long)) * back to the correct page tables. */ ret = __cpu_suspend(arg, fn, __mpidr); + + unpause_graph_tracing(); + if (ret == 0) { cpu_switch_mm(mm->pgd, mm); local_flush_bp_all(); @@ -46,7 +57,13 @@ int cpu_suspend(unsigned long arg, int (*fn)(unsigned long)) int cpu_suspend(unsigned long arg, int (*fn)(unsigned long)) { u32 __mpidr = cpu_logical_map(smp_processor_id()); - return __cpu_suspend(arg, fn, __mpidr); + int ret; + + pause_graph_tracing(); + ret = __cpu_suspend(arg, fn, __mpidr); + unpause_graph_tracing(); + + return ret; } #define idmap_pgd NULL #endif diff --git a/arch/arm64/boot/dts/marvell/armada-37xx.dtsi b/arch/arm64/boot/dts/marvell/armada-37xx.dtsi index d9531e242eb4c..3a611250f598d 100644 --- a/arch/arm64/boot/dts/marvell/armada-37xx.dtsi +++ b/arch/arm64/boot/dts/marvell/armada-37xx.dtsi @@ -143,7 +143,8 @@ }; nb_periph_clk: nb-periph-clk@13000 { - compatible = "marvell,armada-3700-periph-clock-nb"; + compatible = "marvell,armada-3700-periph-clock-nb", + "syscon"; reg = <0x13000 0x100>; clocks = <&tbg 0>, <&tbg 1>, <&tbg 2>, <&tbg 3>, <&xtalclk>; diff --git a/arch/arm64/boot/dts/mediatek/mt8173.dtsi b/arch/arm64/boot/dts/mediatek/mt8173.dtsi index bd9fc50ac1540..12837523dac8c 100644 --- a/arch/arm64/boot/dts/mediatek/mt8173.dtsi +++ b/arch/arm64/boot/dts/mediatek/mt8173.dtsi @@ -1111,7 +1111,7 @@ <&mmsys CLK_MM_DSI1_DIGITAL>, <&mipi_tx1>; clock-names = "engine", "digital", "hs"; - phy = <&mipi_tx1>; + phys = <&mipi_tx1>; phy-names = "dphy"; status = "disabled"; }; diff --git a/arch/arm64/boot/dts/socionext/uniphier-ld20.dtsi b/arch/arm64/boot/dts/socionext/uniphier-ld20.dtsi index caf112629caad..62429c412b335 100644 --- a/arch/arm64/boot/dts/socionext/uniphier-ld20.dtsi +++ b/arch/arm64/boot/dts/socionext/uniphier-ld20.dtsi @@ -610,7 +610,7 @@ clocks = <&sys_clk 6>; reset-names = "ether"; resets = <&sys_rst 6>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; local-mac-address = [00 00 00 00 00 00]; socionext,syscon-phy-mode = <&soc_glue 0>; diff --git a/arch/arm64/boot/dts/socionext/uniphier-pxs3.dtsi b/arch/arm64/boot/dts/socionext/uniphier-pxs3.dtsi index 2a4cf427f5d37..8fe9a57b95620 100644 --- a/arch/arm64/boot/dts/socionext/uniphier-pxs3.dtsi +++ b/arch/arm64/boot/dts/socionext/uniphier-pxs3.dtsi @@ -416,7 +416,7 @@ clocks = <&sys_clk 6>; reset-names = "ether"; resets = <&sys_rst 6>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; local-mac-address = [00 00 00 00 00 00]; socionext,syscon-phy-mode = <&soc_glue 0>; @@ -437,7 +437,7 @@ clocks = <&sys_clk 7>; reset-names = "ether"; resets = <&sys_rst 7>; - phy-mode = "rgmii"; + phy-mode = "rgmii-id"; local-mac-address = [00 00 00 00 00 00]; socionext,syscon-phy-mode = <&soc_glue 1>; diff --git a/arch/arm64/include/asm/kvm_host.h b/arch/arm64/include/asm/kvm_host.h index 151e69a93e341..07472c138ced9 100644 --- a/arch/arm64/include/asm/kvm_host.h +++ b/arch/arm64/include/asm/kvm_host.h @@ -455,6 +455,7 @@ static inline void kvm_arch_sched_in(struct kvm_vcpu *vcpu, int cpu) {} static inline void kvm_arch_vcpu_block_finish(struct kvm_vcpu *vcpu) {} void kvm_arm_init_debug(void); +void kvm_arm_vcpu_init_debug(struct kvm_vcpu *vcpu); void kvm_arm_setup_debug(struct kvm_vcpu *vcpu); void kvm_arm_clear_debug(struct kvm_vcpu *vcpu); void kvm_arm_reset_debug_ptr(struct kvm_vcpu *vcpu); diff --git a/arch/arm64/kernel/vdso/gettimeofday.S b/arch/arm64/kernel/vdso/gettimeofday.S index 856fee6d35129..b6faf8b5d1fe6 100644 --- a/arch/arm64/kernel/vdso/gettimeofday.S +++ b/arch/arm64/kernel/vdso/gettimeofday.S @@ -227,7 +227,7 @@ realtime: seqcnt_check fail=realtime get_ts_realtime res_sec=x10, res_nsec=x11, \ clock_nsec=x15, xtime_sec=x13, xtime_nsec=x14, nsec_to_sec=x9 - clock_gettime_return, shift=1 + clock_gettime_return shift=1 ALIGN monotonic: @@ -250,7 +250,7 @@ monotonic: clock_nsec=x15, xtime_sec=x13, xtime_nsec=x14, nsec_to_sec=x9 add_ts sec=x10, nsec=x11, ts_sec=x3, ts_nsec=x4, nsec_to_sec=x9 - clock_gettime_return, shift=1 + clock_gettime_return shift=1 ALIGN monotonic_raw: @@ -271,7 +271,7 @@ monotonic_raw: clock_nsec=x15, nsec_to_sec=x9 add_ts sec=x10, nsec=x11, ts_sec=x13, ts_nsec=x14, nsec_to_sec=x9 - clock_gettime_return, shift=1 + clock_gettime_return shift=1 ALIGN realtime_coarse: diff --git a/arch/arm64/kernel/vdso/vdso.lds.S b/arch/arm64/kernel/vdso/vdso.lds.S index beca249bc2f39..b3e6c4d5b75c8 100644 --- a/arch/arm64/kernel/vdso/vdso.lds.S +++ b/arch/arm64/kernel/vdso/vdso.lds.S @@ -39,6 +39,13 @@ SECTIONS .gnu.version_d : { *(.gnu.version_d) } .gnu.version_r : { *(.gnu.version_r) } + /* + * Discard .note.gnu.property sections which are unused and have + * different alignment requirement from vDSO note sections. + */ + /DISCARD/ : { + *(.note.GNU-stack .note.gnu.property) + } .note : { *(.note.*) } :text :note . = ALIGN(16); @@ -59,7 +66,6 @@ SECTIONS PROVIDE(end = .); /DISCARD/ : { - *(.note.GNU-stack) *(.data .data.* .gnu.linkonce.d.* .sdata*) *(.bss .sbss .dynbss .dynsbss) } diff --git a/arch/arm64/kvm/debug.c b/arch/arm64/kvm/debug.c index 3606f6b890942..7fe195ef7c3fd 100644 --- a/arch/arm64/kvm/debug.c +++ b/arch/arm64/kvm/debug.c @@ -79,6 +79,64 @@ void kvm_arm_init_debug(void) __this_cpu_write(mdcr_el2, kvm_call_hyp(__kvm_get_mdcr_el2)); } +/** + * kvm_arm_setup_mdcr_el2 - configure vcpu mdcr_el2 value + * + * @vcpu: the vcpu pointer + * + * This ensures we will trap access to: + * - Performance monitors (MDCR_EL2_TPM/MDCR_EL2_TPMCR) + * - Debug ROM Address (MDCR_EL2_TDRA) + * - OS related registers (MDCR_EL2_TDOSA) + * - Statistical profiler (MDCR_EL2_TPMS/MDCR_EL2_E2PB) + * - Self-hosted Trace Filter controls (MDCR_EL2_TTRF) + */ +static void kvm_arm_setup_mdcr_el2(struct kvm_vcpu *vcpu) +{ + /* + * This also clears MDCR_EL2_E2PB_MASK to disable guest access + * to the profiling buffer. + */ + vcpu->arch.mdcr_el2 = __this_cpu_read(mdcr_el2) & MDCR_EL2_HPMN_MASK; + vcpu->arch.mdcr_el2 |= (MDCR_EL2_TPM | + MDCR_EL2_TPMS | + MDCR_EL2_TTRF | + MDCR_EL2_TPMCR | + MDCR_EL2_TDRA | + MDCR_EL2_TDOSA); + + /* Is the VM being debugged by userspace? */ + if (vcpu->guest_debug) + /* Route all software debug exceptions to EL2 */ + vcpu->arch.mdcr_el2 |= MDCR_EL2_TDE; + + /* + * Trap debug register access when one of the following is true: + * - Userspace is using the hardware to debug the guest + * (KVM_GUESTDBG_USE_HW is set). + * - The guest is not using debug (KVM_ARM64_DEBUG_DIRTY is clear). + */ + if ((vcpu->guest_debug & KVM_GUESTDBG_USE_HW) || + !(vcpu->arch.flags & KVM_ARM64_DEBUG_DIRTY)) + vcpu->arch.mdcr_el2 |= MDCR_EL2_TDA; + + trace_kvm_arm_set_dreg32("MDCR_EL2", vcpu->arch.mdcr_el2); +} + +/** + * kvm_arm_vcpu_init_debug - setup vcpu debug traps + * + * @vcpu: the vcpu pointer + * + * Set vcpu initial mdcr_el2 value. + */ +void kvm_arm_vcpu_init_debug(struct kvm_vcpu *vcpu) +{ + preempt_disable(); + kvm_arm_setup_mdcr_el2(vcpu); + preempt_enable(); +} + /** * kvm_arm_reset_debug_ptr - reset the debug ptr to point to the vcpu state */ @@ -94,13 +152,7 @@ void kvm_arm_reset_debug_ptr(struct kvm_vcpu *vcpu) * @vcpu: the vcpu pointer * * This is called before each entry into the hypervisor to setup any - * debug related registers. Currently this just ensures we will trap - * access to: - * - Performance monitors (MDCR_EL2_TPM/MDCR_EL2_TPMCR) - * - Debug ROM Address (MDCR_EL2_TDRA) - * - OS related registers (MDCR_EL2_TDOSA) - * - Statistical profiler (MDCR_EL2_TPMS/MDCR_EL2_E2PB) - * - Self-hosted Trace Filter controls (MDCR_EL2_TTRF) + * debug related registers. * * Additionally, KVM only traps guest accesses to the debug registers if * the guest is not actively using them (see the KVM_ARM64_DEBUG_DIRTY @@ -112,28 +164,14 @@ void kvm_arm_reset_debug_ptr(struct kvm_vcpu *vcpu) void kvm_arm_setup_debug(struct kvm_vcpu *vcpu) { - bool trap_debug = !(vcpu->arch.flags & KVM_ARM64_DEBUG_DIRTY); unsigned long mdscr, orig_mdcr_el2 = vcpu->arch.mdcr_el2; trace_kvm_arm_setup_debug(vcpu, vcpu->guest_debug); - /* - * This also clears MDCR_EL2_E2PB_MASK to disable guest access - * to the profiling buffer. - */ - vcpu->arch.mdcr_el2 = __this_cpu_read(mdcr_el2) & MDCR_EL2_HPMN_MASK; - vcpu->arch.mdcr_el2 |= (MDCR_EL2_TPM | - MDCR_EL2_TPMS | - MDCR_EL2_TTRF | - MDCR_EL2_TPMCR | - MDCR_EL2_TDRA | - MDCR_EL2_TDOSA); + kvm_arm_setup_mdcr_el2(vcpu); /* Is Guest debugging in effect? */ if (vcpu->guest_debug) { - /* Route all software debug exceptions to EL2 */ - vcpu->arch.mdcr_el2 |= MDCR_EL2_TDE; - /* Save guest debug state */ save_guest_debug_regs(vcpu); @@ -187,7 +225,6 @@ void kvm_arm_setup_debug(struct kvm_vcpu *vcpu) vcpu->arch.debug_ptr = &vcpu->arch.external_debug_state; vcpu->arch.flags |= KVM_ARM64_DEBUG_DIRTY; - trap_debug = true; trace_kvm_arm_set_regset("BKPTS", get_num_brps(), &vcpu->arch.debug_ptr->dbg_bcr[0], @@ -202,10 +239,6 @@ void kvm_arm_setup_debug(struct kvm_vcpu *vcpu) BUG_ON(!vcpu->guest_debug && vcpu->arch.debug_ptr != &vcpu->arch.vcpu_debug_state); - /* Trap debug register access */ - if (trap_debug) - vcpu->arch.mdcr_el2 |= MDCR_EL2_TDA; - /* If KDE or MDE are set, perform a full save/restore cycle. */ if (vcpu_read_sys_reg(vcpu, MDSCR_EL1) & (DBG_MDSCR_KDE | DBG_MDSCR_MDE)) vcpu->arch.flags |= KVM_ARM64_DEBUG_DIRTY; @@ -214,7 +247,6 @@ void kvm_arm_setup_debug(struct kvm_vcpu *vcpu) if (has_vhe() && orig_mdcr_el2 != vcpu->arch.mdcr_el2) write_sysreg(vcpu->arch.mdcr_el2, mdcr_el2); - trace_kvm_arm_set_dreg32("MDCR_EL2", vcpu->arch.mdcr_el2); trace_kvm_arm_set_dreg32("MDSCR_EL1", vcpu_read_sys_reg(vcpu, MDSCR_EL1)); } diff --git a/arch/ia64/include/asm/module.h b/arch/ia64/include/asm/module.h index f319144260ce1..9fbf32e6e8813 100644 --- a/arch/ia64/include/asm/module.h +++ b/arch/ia64/include/asm/module.h @@ -14,16 +14,20 @@ struct elf64_shdr; /* forward declration */ struct mod_arch_specific { + /* Used only at module load time. */ struct elf64_shdr *core_plt; /* core PLT section */ struct elf64_shdr *init_plt; /* init PLT section */ struct elf64_shdr *got; /* global offset table */ struct elf64_shdr *opd; /* official procedure descriptors */ struct elf64_shdr *unwind; /* unwind-table section */ unsigned long gp; /* global-pointer for module */ + unsigned int next_got_entry; /* index of next available got entry */ + /* Used at module run and cleanup time. */ void *core_unw_table; /* core unwind-table cookie returned by unwinder */ void *init_unw_table; /* init unwind-table cookie returned by unwinder */ - unsigned int next_got_entry; /* index of next available got entry */ + void *opd_addr; /* symbolize uses .opd to get to actual function */ + unsigned long opd_size; }; #define MODULE_PROC_FAMILY "ia64" diff --git a/arch/ia64/kernel/module.c b/arch/ia64/kernel/module.c index 1a42ba885188a..ee693c8cec498 100644 --- a/arch/ia64/kernel/module.c +++ b/arch/ia64/kernel/module.c @@ -905,9 +905,31 @@ register_unwind_table (struct module *mod) int module_finalize (const Elf_Ehdr *hdr, const Elf_Shdr *sechdrs, struct module *mod) { + struct mod_arch_specific *mas = &mod->arch; + DEBUGP("%s: init: entry=%p\n", __func__, mod->init); - if (mod->arch.unwind) + if (mas->unwind) register_unwind_table(mod); + + /* + * ".opd" was already relocated to the final destination. Store + * it's address for use in symbolizer. + */ + mas->opd_addr = (void *)mas->opd->sh_addr; + mas->opd_size = mas->opd->sh_size; + + /* + * Module relocation was already done at this point. Section + * headers are about to be deleted. Wipe out load-time context. + */ + mas->core_plt = NULL; + mas->init_plt = NULL; + mas->got = NULL; + mas->opd = NULL; + mas->unwind = NULL; + mas->gp = 0; + mas->next_got_entry = 0; + return 0; } @@ -926,10 +948,9 @@ module_arch_cleanup (struct module *mod) void *dereference_module_function_descriptor(struct module *mod, void *ptr) { - Elf64_Shdr *opd = mod->arch.opd; + struct mod_arch_specific *mas = &mod->arch; - if (ptr < (void *)opd->sh_addr || - ptr >= (void *)(opd->sh_addr + opd->sh_size)) + if (ptr < mas->opd_addr || ptr >= mas->opd_addr + mas->opd_size) return ptr; return dereference_function_descriptor(ptr); diff --git a/arch/ia64/scripts/unwcheck.py b/arch/ia64/scripts/unwcheck.py index c55276e31b6b6..bfd1b671e35fc 100644 --- a/arch/ia64/scripts/unwcheck.py +++ b/arch/ia64/scripts/unwcheck.py @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/env python # SPDX-License-Identifier: GPL-2.0 # # Usage: unwcheck.py FILE diff --git a/arch/mips/include/asm/div64.h b/arch/mips/include/asm/div64.h index dc5ea57364408..ceece76fc971a 100644 --- a/arch/mips/include/asm/div64.h +++ b/arch/mips/include/asm/div64.h @@ -1,5 +1,5 @@ /* - * Copyright (C) 2000, 2004 Maciej W. Rozycki + * Copyright (C) 2000, 2004, 2021 Maciej W. Rozycki * Copyright (C) 2003, 07 Ralf Baechle (ralf@linux-mips.org) * * This file is subject to the terms and conditions of the GNU General Public @@ -9,25 +9,18 @@ #ifndef __ASM_DIV64_H #define __ASM_DIV64_H -#include - -#if BITS_PER_LONG == 64 +#include -#include +#if BITS_PER_LONG == 32 /* * No traps on overflows for any of these... */ -#define __div64_32(n, base) \ -({ \ +#define do_div64_32(res, high, low, base) ({ \ unsigned long __cf, __tmp, __tmp2, __i; \ unsigned long __quot32, __mod32; \ - unsigned long __high, __low; \ - unsigned long long __n; \ \ - __high = *__n >> 32; \ - __low = __n; \ __asm__( \ " .set push \n" \ " .set noat \n" \ @@ -51,18 +44,48 @@ " subu %0, %0, %z6 \n" \ " addiu %2, %2, 1 \n" \ "3: \n" \ - " bnez %4, 0b\n\t" \ - " srl %5, %1, 0x1f\n\t" \ + " bnez %4, 0b \n" \ + " srl %5, %1, 0x1f \n" \ " .set pop" \ : "=&r" (__mod32), "=&r" (__tmp), \ "=&r" (__quot32), "=&r" (__cf), \ "=&r" (__i), "=&r" (__tmp2) \ - : "Jr" (base), "0" (__high), "1" (__low)); \ + : "Jr" (base), "0" (high), "1" (low)); \ \ - (__n) = __quot32; \ + (res) = __quot32; \ __mod32; \ }) -#endif /* BITS_PER_LONG == 64 */ +#define __div64_32(n, base) ({ \ + unsigned long __upper, __low, __high, __radix; \ + unsigned long long __quot; \ + unsigned long long __div; \ + unsigned long __mod; \ + \ + __div = (*n); \ + __radix = (base); \ + \ + __high = __div >> 32; \ + __low = __div; \ + \ + if (__high < __radix) { \ + __upper = __high; \ + __high = 0; \ + } else { \ + __upper = __high % __radix; \ + __high /= __radix; \ + } \ + \ + __mod = do_div64_32(__low, __upper, __low, __radix); \ + \ + __quot = __high; \ + __quot = __quot << 32 | __low; \ + (*n) = __quot; \ + __mod; \ +}) + +#endif /* BITS_PER_LONG == 32 */ + +#include #endif /* __ASM_DIV64_H */ diff --git a/arch/mips/pci/pci-legacy.c b/arch/mips/pci/pci-legacy.c index 3c3b1e6abb535..e8b0751d5b76b 100644 --- a/arch/mips/pci/pci-legacy.c +++ b/arch/mips/pci/pci-legacy.c @@ -169,8 +169,13 @@ void pci_load_of_ranges(struct pci_controller *hose, struct device_node *node) res = hose->mem_resource; break; } - if (res != NULL) - of_pci_range_to_resource(&range, node, res); + if (res != NULL) { + res->name = node->full_name; + res->flags = range.flags; + res->start = range.cpu_addr; + res->end = range.cpu_addr + range.size - 1; + res->parent = res->child = res->sibling = NULL; + } } } diff --git a/arch/mips/pci/pci-mt7620.c b/arch/mips/pci/pci-mt7620.c index f6b77788124af..5ae11aeff4b78 100644 --- a/arch/mips/pci/pci-mt7620.c +++ b/arch/mips/pci/pci-mt7620.c @@ -33,6 +33,7 @@ #define RALINK_GPIOMODE 0x60 #define PPLL_CFG1 0x9c +#define PPLL_LD BIT(23) #define PPLL_DRV 0xa0 #define PDRV_SW_SET BIT(31) @@ -242,8 +243,8 @@ static int mt7620_pci_hw_init(struct platform_device *pdev) rt_sysc_m32(0, RALINK_PCIE0_CLK_EN, RALINK_CLKCFG1); mdelay(100); - if (!(rt_sysc_r32(PPLL_CFG1) & PDRV_SW_SET)) { - dev_err(&pdev->dev, "MT7620 PPLL unlock\n"); + if (!(rt_sysc_r32(PPLL_CFG1) & PPLL_LD)) { + dev_err(&pdev->dev, "pcie PLL not locked, aborting init\n"); reset_control_assert(rstpcie0); rt_sysc_m32(RALINK_PCIE0_CLK_EN, 0, RALINK_CLKCFG1); return -1; diff --git a/arch/mips/pci/pci-rt2880.c b/arch/mips/pci/pci-rt2880.c index 711cdccdf65ba..f7926a964441b 100644 --- a/arch/mips/pci/pci-rt2880.c +++ b/arch/mips/pci/pci-rt2880.c @@ -183,7 +183,6 @@ static inline void rt2880_pci_write_u32(unsigned long reg, u32 val) int pcibios_map_irq(const struct pci_dev *dev, u8 slot, u8 pin) { - u16 cmd; int irq = -1; if (dev->bus->number != 0) @@ -191,8 +190,6 @@ int pcibios_map_irq(const struct pci_dev *dev, u8 slot, u8 pin) switch (PCI_SLOT(dev->devfn)) { case 0x00: - rt2880_pci_write_u32(PCI_BASE_ADDRESS_0, 0x08000000); - (void) rt2880_pci_read_u32(PCI_BASE_ADDRESS_0); break; case 0x11: irq = RT288X_CPU_IRQ_PCI; @@ -204,16 +201,6 @@ int pcibios_map_irq(const struct pci_dev *dev, u8 slot, u8 pin) break; } - pci_write_config_byte((struct pci_dev *) dev, - PCI_CACHE_LINE_SIZE, 0x14); - pci_write_config_byte((struct pci_dev *) dev, PCI_LATENCY_TIMER, 0xFF); - pci_read_config_word((struct pci_dev *) dev, PCI_COMMAND, &cmd); - cmd |= PCI_COMMAND_MASTER | PCI_COMMAND_IO | PCI_COMMAND_MEMORY | - PCI_COMMAND_INVALIDATE | PCI_COMMAND_FAST_BACK | - PCI_COMMAND_SERR | PCI_COMMAND_WAIT | PCI_COMMAND_PARITY; - pci_write_config_word((struct pci_dev *) dev, PCI_COMMAND, cmd); - pci_write_config_byte((struct pci_dev *) dev, PCI_INTERRUPT_LINE, - dev->irq); return irq; } @@ -252,6 +239,30 @@ static int rt288x_pci_probe(struct platform_device *pdev) int pcibios_plat_dev_init(struct pci_dev *dev) { + static bool slot0_init; + + /* + * Nobody seems to initialize slot 0, but this platform requires it, so + * do it once when some other slot is being enabled. The PCI subsystem + * should configure other slots properly, so no need to do anything + * special for those. + */ + if (!slot0_init && dev->bus->number == 0) { + u16 cmd; + u32 bar0; + + slot0_init = true; + + pci_bus_write_config_dword(dev->bus, 0, PCI_BASE_ADDRESS_0, + 0x08000000); + pci_bus_read_config_dword(dev->bus, 0, PCI_BASE_ADDRESS_0, + &bar0); + + pci_bus_read_config_word(dev->bus, 0, PCI_COMMAND, &cmd); + cmd |= PCI_COMMAND_MASTER | PCI_COMMAND_IO | PCI_COMMAND_MEMORY; + pci_bus_write_config_word(dev->bus, 0, PCI_COMMAND, cmd); + } + return 0; } diff --git a/arch/powerpc/Kconfig b/arch/powerpc/Kconfig index 6dd2a14e1ebcd..f0e09d5f0bedd 100644 --- a/arch/powerpc/Kconfig +++ b/arch/powerpc/Kconfig @@ -208,7 +208,7 @@ config PPC select HAVE_MEMBLOCK_NODE_MAP select HAVE_MOD_ARCH_SPECIFIC select HAVE_NMI if PERF_EVENTS || (PPC64 && PPC_BOOK3S) - select HAVE_HARDLOCKUP_DETECTOR_ARCH if (PPC64 && PPC_BOOK3S) + select HAVE_HARDLOCKUP_DETECTOR_ARCH if PPC64 && PPC_BOOK3S && SMP select HAVE_OPROFILE select HAVE_OPTPROBES if PPC64 select HAVE_PERF_EVENTS diff --git a/arch/powerpc/Kconfig.debug b/arch/powerpc/Kconfig.debug index fd63cd914a74f..ffe0cf0f0bea2 100644 --- a/arch/powerpc/Kconfig.debug +++ b/arch/powerpc/Kconfig.debug @@ -350,6 +350,7 @@ config PPC_EARLY_DEBUG_CPM_ADDR config FAIL_IOMMU bool "Fault-injection capability for IOMMU" depends on FAULT_INJECTION + depends on PCI || IBMVIO help Provide fault-injection capability for IOMMU. Each device can be selectively enabled via the fail_iommu property. diff --git a/arch/powerpc/include/asm/book3s/64/radix.h b/arch/powerpc/include/asm/book3s/64/radix.h index da01badef0cbc..04b2bffbc5c95 100644 --- a/arch/powerpc/include/asm/book3s/64/radix.h +++ b/arch/powerpc/include/asm/book3s/64/radix.h @@ -204,8 +204,10 @@ static inline void radix__set_pte_at(struct mm_struct *mm, unsigned long addr, * from ptesync, it should probably go into update_mmu_cache, rather * than set_pte_at (which is used to set ptes unrelated to faults). * - * Spurious faults to vmalloc region are not tolerated, so there is - * a ptesync in flush_cache_vmap. + * Spurious faults from the kernel memory are not tolerated, so there + * is a ptesync in flush_cache_vmap, and __map_kernel_page() follows + * the pte update sequence from ISA Book III 6.10 Translation Table + * Update Synchronization Requirements. */ } diff --git a/arch/powerpc/include/uapi/asm/errno.h b/arch/powerpc/include/uapi/asm/errno.h index cc79856896a19..4ba87de32be00 100644 --- a/arch/powerpc/include/uapi/asm/errno.h +++ b/arch/powerpc/include/uapi/asm/errno.h @@ -2,6 +2,7 @@ #ifndef _ASM_POWERPC_ERRNO_H #define _ASM_POWERPC_ERRNO_H +#undef EDEADLOCK #include #undef EDEADLOCK diff --git a/arch/powerpc/kernel/eeh.c b/arch/powerpc/kernel/eeh.c index d123cba0992d0..44bb522fb4a20 100644 --- a/arch/powerpc/kernel/eeh.c +++ b/arch/powerpc/kernel/eeh.c @@ -364,14 +364,11 @@ static inline unsigned long eeh_token_to_phys(unsigned long token) pa = pte_pfn(*ptep); /* On radix we can do hugepage mappings for io, so handle that */ - if (hugepage_shift) { - pa <<= hugepage_shift; - pa |= token & ((1ul << hugepage_shift) - 1); - } else { - pa <<= PAGE_SHIFT; - pa |= token & (PAGE_SIZE - 1); - } + if (!hugepage_shift) + hugepage_shift = PAGE_SHIFT; + pa <<= PAGE_SHIFT; + pa |= token & ((1ul << hugepage_shift) - 1); return pa; } diff --git a/arch/powerpc/kernel/iommu.c b/arch/powerpc/kernel/iommu.c index f0dc680e659af..c3d2d5cd7c10c 100644 --- a/arch/powerpc/kernel/iommu.c +++ b/arch/powerpc/kernel/iommu.c @@ -1030,7 +1030,7 @@ int iommu_take_ownership(struct iommu_table *tbl) spin_lock_irqsave(&tbl->large_pool.lock, flags); for (i = 0; i < tbl->nr_pools; i++) - spin_lock(&tbl->pools[i].lock); + spin_lock_nest_lock(&tbl->pools[i].lock, &tbl->large_pool.lock); if (tbl->it_offset == 0) clear_bit(0, tbl->it_map); @@ -1059,7 +1059,7 @@ void iommu_release_ownership(struct iommu_table *tbl) spin_lock_irqsave(&tbl->large_pool.lock, flags); for (i = 0; i < tbl->nr_pools; i++) - spin_lock(&tbl->pools[i].lock); + spin_lock_nest_lock(&tbl->pools[i].lock, &tbl->large_pool.lock); memset(tbl->it_map, 0, sz); diff --git a/arch/powerpc/kernel/prom.c b/arch/powerpc/kernel/prom.c index fd04692412db3..f8c49e5d4bd3b 100644 --- a/arch/powerpc/kernel/prom.c +++ b/arch/powerpc/kernel/prom.c @@ -266,7 +266,7 @@ static struct feature_property { }; #if defined(CONFIG_44x) && defined(CONFIG_PPC_FPU) -static inline void identical_pvr_fixup(unsigned long node) +static __init void identical_pvr_fixup(unsigned long node) { unsigned int pvr; const char *model = of_get_flat_dt_prop(node, "model", NULL); diff --git a/arch/powerpc/kernel/smp.c b/arch/powerpc/kernel/smp.c index 6dc43205382ba..a9ec4467705ca 100644 --- a/arch/powerpc/kernel/smp.c +++ b/arch/powerpc/kernel/smp.c @@ -1032,6 +1032,9 @@ void start_secondary(void *unused) vdso_getcpu_init(); #endif + set_numa_node(numa_cpu_lookup_table[cpu]); + set_numa_mem(local_memory_node(numa_cpu_lookup_table[cpu])); + /* Update topology CPU masks */ add_cpu_to_masks(cpu); @@ -1042,9 +1045,6 @@ void start_secondary(void *unused) if (!cpumask_equal(cpu_l2_cache_mask(cpu), cpu_sibling_mask(cpu))) shared_caches = true; - set_numa_node(numa_cpu_lookup_table[cpu]); - set_numa_mem(local_memory_node(numa_cpu_lookup_table[cpu])); - smp_wmb(); notify_cpu_starting(cpu); set_cpu_online(cpu, true); diff --git a/arch/powerpc/lib/feature-fixups.c b/arch/powerpc/lib/feature-fixups.c index 065a3426f0ebc..1561094ea4a58 100644 --- a/arch/powerpc/lib/feature-fixups.c +++ b/arch/powerpc/lib/feature-fixups.c @@ -18,6 +18,7 @@ #include #include #include +#include #include #include #include @@ -225,11 +226,25 @@ void do_stf_exit_barrier_fixups(enum stf_barrier_type types) : "unknown"); } +static int __do_stf_barrier_fixups(void *data) +{ + enum stf_barrier_type *types = data; + + do_stf_entry_barrier_fixups(*types); + do_stf_exit_barrier_fixups(*types); + + return 0; +} void do_stf_barrier_fixups(enum stf_barrier_type types) { - do_stf_entry_barrier_fixups(types); - do_stf_exit_barrier_fixups(types); + /* + * The call to the fallback entry flush, and the fallback/sync-ori exit + * flush can not be safely patched in/out while other CPUs are executing + * them. So call __do_stf_barrier_fixups() on one CPU while all other CPUs + * spin in the stop machine core with interrupts hard disabled. + */ + stop_machine(__do_stf_barrier_fixups, &types, NULL); } void do_uaccess_flush_fixups(enum l1d_flush_type types) @@ -282,8 +297,9 @@ void do_uaccess_flush_fixups(enum l1d_flush_type types) : "unknown"); } -void do_entry_flush_fixups(enum l1d_flush_type types) +static int __do_entry_flush_fixups(void *data) { + enum l1d_flush_type types = *(enum l1d_flush_type *)data; unsigned int instrs[3], *dest; long *start, *end; int i; @@ -334,6 +350,19 @@ void do_entry_flush_fixups(enum l1d_flush_type types) : "ori type" : (types & L1D_FLUSH_MTTRIG) ? "mttrig type" : "unknown"); + + return 0; +} + +void do_entry_flush_fixups(enum l1d_flush_type types) +{ + /* + * The call to the fallback flush can not be safely patched in/out while + * other CPUs are executing it. So call __do_entry_flush_fixups() on one + * CPU while all other CPUs spin in the stop machine core with interrupts + * hard disabled. + */ + stop_machine(__do_entry_flush_fixups, &types, NULL); } void do_rfi_flush_fixups(enum l1d_flush_type types) diff --git a/arch/powerpc/mm/pgtable-radix.c b/arch/powerpc/mm/pgtable-radix.c index 5404a631d5834..9ee235fca4278 100644 --- a/arch/powerpc/mm/pgtable-radix.c +++ b/arch/powerpc/mm/pgtable-radix.c @@ -115,7 +115,7 @@ static int early_map_kernel_page(unsigned long ea, unsigned long pa, set_the_pte: set_pte_at(&init_mm, ea, ptep, pfn_pte(pfn, flags)); - smp_wmb(); + asm volatile("ptesync": : :"memory"); return 0; } @@ -169,7 +169,7 @@ static int __map_kernel_page(unsigned long ea, unsigned long pa, set_the_pte: set_pte_at(&init_mm, ea, ptep, pfn_pte(pfn, flags)); - smp_wmb(); + asm volatile("ptesync": : :"memory"); return 0; } diff --git a/arch/powerpc/perf/isa207-common.c b/arch/powerpc/perf/isa207-common.c index 69a2dc2b16cf1..a1ff4142cc6a4 100644 --- a/arch/powerpc/perf/isa207-common.c +++ b/arch/powerpc/perf/isa207-common.c @@ -359,8 +359,8 @@ ebb_bhrb: * EBB events are pinned & exclusive, so this should never actually * hit, but we leave it as a fallback in case. */ - mask |= CNST_EBB_VAL(ebb); - value |= CNST_EBB_MASK; + mask |= CNST_EBB_MASK; + value |= CNST_EBB_VAL(ebb); *maskp = mask; *valp = value; diff --git a/arch/powerpc/platforms/52xx/lite5200_sleep.S b/arch/powerpc/platforms/52xx/lite5200_sleep.S index 3a9969c429b39..054f927bfef93 100644 --- a/arch/powerpc/platforms/52xx/lite5200_sleep.S +++ b/arch/powerpc/platforms/52xx/lite5200_sleep.S @@ -181,7 +181,7 @@ sram_code: udelay: /* r11 - tb_ticks_per_usec, r12 - usecs, overwrites r13 */ mullw r12, r12, r11 mftb r13 /* start */ - addi r12, r13, r12 /* end */ + add r12, r13, r12 /* end */ 1: mftb r13 /* current */ cmp cr0, r13, r12 diff --git a/arch/powerpc/platforms/pseries/hotplug-cpu.c b/arch/powerpc/platforms/pseries/hotplug-cpu.c index 1d3f9313c02ff..8bfb97d07d100 100644 --- a/arch/powerpc/platforms/pseries/hotplug-cpu.c +++ b/arch/powerpc/platforms/pseries/hotplug-cpu.c @@ -95,9 +95,6 @@ static void rtas_stop_self(void) BUG_ON(rtas_stop_self_token == RTAS_UNKNOWN_SERVICE); - printk("cpu %u (hwid %u) Ready to die...\n", - smp_processor_id(), hard_smp_processor_id()); - rtas_call_unlocked(&args, rtas_stop_self_token, 0, 1, NULL); panic("Alas, I survived.\n"); diff --git a/arch/powerpc/platforms/pseries/pci_dlpar.c b/arch/powerpc/platforms/pseries/pci_dlpar.c index 561917fa54a8a..afca4b737e80f 100644 --- a/arch/powerpc/platforms/pseries/pci_dlpar.c +++ b/arch/powerpc/platforms/pseries/pci_dlpar.c @@ -66,6 +66,7 @@ EXPORT_SYMBOL_GPL(init_phb_dynamic); int remove_phb_dynamic(struct pci_controller *phb) { struct pci_bus *b = phb->bus; + struct pci_host_bridge *host_bridge = to_pci_host_bridge(b->bridge); struct resource *res; int rc, i; @@ -92,7 +93,8 @@ int remove_phb_dynamic(struct pci_controller *phb) /* Remove the PCI bus and unregister the bridge device from sysfs */ phb->bus = NULL; pci_remove_bus(b); - device_unregister(b->bridge); + host_bridge->bus = NULL; + device_unregister(&host_bridge->dev); /* Now release the IO resource */ if (res->flags & IORESOURCE_IO) diff --git a/arch/riscv/include/asm/ftrace.h b/arch/riscv/include/asm/ftrace.h index 02fbc175142e2..693c3839a7dfe 100644 --- a/arch/riscv/include/asm/ftrace.h +++ b/arch/riscv/include/asm/ftrace.h @@ -10,9 +10,19 @@ #endif #define HAVE_FUNCTION_GRAPH_RET_ADDR_PTR +/* + * Clang prior to 13 had "mcount" instead of "_mcount": + * https://reviews.llvm.org/D98881 + */ +#if defined(CONFIG_CC_IS_GCC) || CONFIG_CLANG_VERSION >= 130000 +#define MCOUNT_NAME _mcount +#else +#define MCOUNT_NAME mcount +#endif + #define ARCH_SUPPORTS_FTRACE_OPS 1 #ifndef __ASSEMBLY__ -void _mcount(void); +void MCOUNT_NAME(void); static inline unsigned long ftrace_call_adjust(unsigned long addr) { return addr; @@ -33,7 +43,7 @@ struct dyn_arch_ftrace { * both auipc and jalr at the same time. */ -#define MCOUNT_ADDR ((unsigned long)_mcount) +#define MCOUNT_ADDR ((unsigned long)MCOUNT_NAME) #define JALR_SIGN_MASK (0x00000800) #define JALR_OFFSET_MASK (0x00000fff) #define AUIPC_OFFSET_MASK (0xfffff000) diff --git a/arch/riscv/kernel/mcount.S b/arch/riscv/kernel/mcount.S index 5721624886a1c..fabddee90d1bd 100644 --- a/arch/riscv/kernel/mcount.S +++ b/arch/riscv/kernel/mcount.S @@ -47,8 +47,8 @@ ENTRY(ftrace_stub) #ifdef CONFIG_DYNAMIC_FTRACE - .global _mcount - .set _mcount, ftrace_stub + .global MCOUNT_NAME + .set MCOUNT_NAME, ftrace_stub #endif ret ENDPROC(ftrace_stub) @@ -79,7 +79,7 @@ EXPORT_SYMBOL(return_to_handler) #endif #ifndef CONFIG_DYNAMIC_FTRACE -ENTRY(_mcount) +ENTRY(MCOUNT_NAME) la t4, ftrace_stub #ifdef CONFIG_FUNCTION_GRAPH_TRACER la t0, ftrace_graph_return @@ -125,6 +125,6 @@ do_trace: jalr t5 RESTORE_ABI_STATE ret -ENDPROC(_mcount) +ENDPROC(MCOUNT_NAME) #endif -EXPORT_SYMBOL(_mcount) +EXPORT_SYMBOL(MCOUNT_NAME) diff --git a/arch/s390/crypto/arch_random.c b/arch/s390/crypto/arch_random.c index dd95cdbd22ce8..4cbb4b6d85a83 100644 --- a/arch/s390/crypto/arch_random.c +++ b/arch/s390/crypto/arch_random.c @@ -53,6 +53,10 @@ static DECLARE_DELAYED_WORK(arch_rng_work, arch_rng_refill_buffer); bool s390_arch_random_generate(u8 *buf, unsigned int nbytes) { + /* max hunk is ARCH_RNG_BUF_SIZE */ + if (nbytes > ARCH_RNG_BUF_SIZE) + return false; + /* lock rng buffer */ if (!spin_trylock(&arch_rng_lock)) return false; diff --git a/arch/s390/kernel/dis.c b/arch/s390/kernel/dis.c index 41925f2206940..01307db4b4dd4 100644 --- a/arch/s390/kernel/dis.c +++ b/arch/s390/kernel/dis.c @@ -558,7 +558,7 @@ void show_code(struct pt_regs *regs) void print_fn_code(unsigned char *code, unsigned long len) { - char buffer[64], *ptr; + char buffer[128], *ptr; int opsize, i; while (len) { diff --git a/arch/s390/kvm/gaccess.h b/arch/s390/kvm/gaccess.h index f4c51756c4623..4c56de5429608 100644 --- a/arch/s390/kvm/gaccess.h +++ b/arch/s390/kvm/gaccess.h @@ -18,17 +18,14 @@ /** * kvm_s390_real_to_abs - convert guest real address to guest absolute address - * @vcpu - guest virtual cpu + * @prefix - guest prefix * @gra - guest real address * * Returns the guest absolute address that corresponds to the passed guest real - * address @gra of a virtual guest cpu by applying its prefix. + * address @gra of by applying the given prefix. */ -static inline unsigned long kvm_s390_real_to_abs(struct kvm_vcpu *vcpu, - unsigned long gra) +static inline unsigned long _kvm_s390_real_to_abs(u32 prefix, unsigned long gra) { - unsigned long prefix = kvm_s390_get_prefix(vcpu); - if (gra < 2 * PAGE_SIZE) gra += prefix; else if (gra >= prefix && gra < prefix + 2 * PAGE_SIZE) @@ -36,6 +33,43 @@ static inline unsigned long kvm_s390_real_to_abs(struct kvm_vcpu *vcpu, return gra; } +/** + * kvm_s390_real_to_abs - convert guest real address to guest absolute address + * @vcpu - guest virtual cpu + * @gra - guest real address + * + * Returns the guest absolute address that corresponds to the passed guest real + * address @gra of a virtual guest cpu by applying its prefix. + */ +static inline unsigned long kvm_s390_real_to_abs(struct kvm_vcpu *vcpu, + unsigned long gra) +{ + return _kvm_s390_real_to_abs(kvm_s390_get_prefix(vcpu), gra); +} + +/** + * _kvm_s390_logical_to_effective - convert guest logical to effective address + * @psw: psw of the guest + * @ga: guest logical address + * + * Convert a guest logical address to an effective address by applying the + * rules of the addressing mode defined by bits 31 and 32 of the given PSW + * (extendended/basic addressing mode). + * + * Depending on the addressing mode, the upper 40 bits (24 bit addressing + * mode), 33 bits (31 bit addressing mode) or no bits (64 bit addressing + * mode) of @ga will be zeroed and the remaining bits will be returned. + */ +static inline unsigned long _kvm_s390_logical_to_effective(psw_t *psw, + unsigned long ga) +{ + if (psw_bits(*psw).eaba == PSW_BITS_AMODE_64BIT) + return ga; + if (psw_bits(*psw).eaba == PSW_BITS_AMODE_31BIT) + return ga & ((1UL << 31) - 1); + return ga & ((1UL << 24) - 1); +} + /** * kvm_s390_logical_to_effective - convert guest logical to effective address * @vcpu: guest virtual cpu @@ -52,13 +86,7 @@ static inline unsigned long kvm_s390_real_to_abs(struct kvm_vcpu *vcpu, static inline unsigned long kvm_s390_logical_to_effective(struct kvm_vcpu *vcpu, unsigned long ga) { - psw_t *psw = &vcpu->arch.sie_block->gpsw; - - if (psw_bits(*psw).eaba == PSW_BITS_AMODE_64BIT) - return ga; - if (psw_bits(*psw).eaba == PSW_BITS_AMODE_31BIT) - return ga & ((1UL << 31) - 1); - return ga & ((1UL << 24) - 1); + return _kvm_s390_logical_to_effective(&vcpu->arch.sie_block->gpsw, ga); } /* diff --git a/arch/s390/kvm/kvm-s390.c b/arch/s390/kvm/kvm-s390.c index 18662c1a93611..71c67a1d2849a 100644 --- a/arch/s390/kvm/kvm-s390.c +++ b/arch/s390/kvm/kvm-s390.c @@ -3624,16 +3624,16 @@ static void store_regs(struct kvm_vcpu *vcpu, struct kvm_run *kvm_run) current->thread.fpu.fpc = vcpu->arch.host_fpregs.fpc; current->thread.fpu.regs = vcpu->arch.host_fpregs.regs; if (MACHINE_HAS_GS) { + preempt_disable(); __ctl_set_bit(2, 4); if (vcpu->arch.gs_enabled) save_gs_cb(current->thread.gs_cb); - preempt_disable(); current->thread.gs_cb = vcpu->arch.host_gscb; restore_gs_cb(vcpu->arch.host_gscb); - preempt_enable(); if (!vcpu->arch.host_gscb) __ctl_clear_bit(2, 4); vcpu->arch.host_gscb = NULL; + preempt_enable(); } /* SIE will save etoken directly into SDNX and therefore kvm_run */ } diff --git a/arch/um/kernel/dyn.lds.S b/arch/um/kernel/dyn.lds.S index 5568cf8823711..8992336254673 100644 --- a/arch/um/kernel/dyn.lds.S +++ b/arch/um/kernel/dyn.lds.S @@ -6,6 +6,12 @@ OUTPUT_ARCH(ELF_ARCH) ENTRY(_start) jiffies = jiffies_64; +VERSION { + { + local: *; + }; +} + SECTIONS { PROVIDE (__executable_start = START); diff --git a/arch/um/kernel/uml.lds.S b/arch/um/kernel/uml.lds.S index 36b07ec09742a..22ff701d9b710 100644 --- a/arch/um/kernel/uml.lds.S +++ b/arch/um/kernel/uml.lds.S @@ -7,6 +7,12 @@ OUTPUT_ARCH(ELF_ARCH) ENTRY(_start) jiffies = jiffies_64; +VERSION { + { + local: *; + }; +} + SECTIONS { /* This must contain the right address - not quite the default ELF one.*/ diff --git a/arch/x86/Kconfig b/arch/x86/Kconfig index af35f5caadbe5..d994501d9179f 100644 --- a/arch/x86/Kconfig +++ b/arch/x86/Kconfig @@ -533,6 +533,7 @@ config X86_UV depends on X86_EXTENDED_PLATFORM depends on NUMA depends on EFI + depends on KEXEC_CORE depends on X86_X2APIC depends on PCI ---help--- diff --git a/arch/x86/Makefile b/arch/x86/Makefile index 6ebdbad21fb2a..65a8722e784c6 100644 --- a/arch/x86/Makefile +++ b/arch/x86/Makefile @@ -40,6 +40,7 @@ REALMODE_CFLAGS += $(call __cc-option, $(CC), $(REALMODE_CFLAGS), -ffreestanding REALMODE_CFLAGS += $(call __cc-option, $(CC), $(REALMODE_CFLAGS), -fno-stack-protector) REALMODE_CFLAGS += $(call __cc-option, $(CC), $(REALMODE_CFLAGS), -Wno-address-of-packed-member) REALMODE_CFLAGS += $(call __cc-option, $(CC), $(REALMODE_CFLAGS), $(cc_stack_align4)) +REALMODE_CFLAGS += $(CLANG_FLAGS) export REALMODE_CFLAGS # BITS is used as extension for files which are available in a 32 bit diff --git a/arch/x86/entry/vdso/vma.c b/arch/x86/entry/vdso/vma.c index 5b8b556dbb12a..46caca4d9141b 100644 --- a/arch/x86/entry/vdso/vma.c +++ b/arch/x86/entry/vdso/vma.c @@ -343,7 +343,7 @@ static void vgetcpu_cpu_init(void *arg) #ifdef CONFIG_NUMA node = cpu_to_node(cpu); #endif - if (static_cpu_has(X86_FEATURE_RDTSCP)) + if (boot_cpu_has(X86_FEATURE_RDTSCP) || boot_cpu_has(X86_FEATURE_RDPID)) write_rdtscp_aux((node << 12) | cpu); /* diff --git a/arch/x86/events/amd/iommu.c b/arch/x86/events/amd/iommu.c index 0014d26391fa6..c08bcba5c3a99 100644 --- a/arch/x86/events/amd/iommu.c +++ b/arch/x86/events/amd/iommu.c @@ -84,12 +84,12 @@ static struct attribute_group amd_iommu_events_group = { }; struct amd_iommu_event_desc { - struct kobj_attribute attr; + struct device_attribute attr; const char *event; }; -static ssize_t _iommu_event_show(struct kobject *kobj, - struct kobj_attribute *attr, char *buf) +static ssize_t _iommu_event_show(struct device *dev, + struct device_attribute *attr, char *buf) { struct amd_iommu_event_desc *event = container_of(attr, struct amd_iommu_event_desc, attr); diff --git a/arch/x86/kernel/cpu/microcode/core.c b/arch/x86/kernel/cpu/microcode/core.c index a96091d44a459..eab4de387ce64 100644 --- a/arch/x86/kernel/cpu/microcode/core.c +++ b/arch/x86/kernel/cpu/microcode/core.c @@ -627,16 +627,16 @@ static ssize_t reload_store(struct device *dev, if (val != 1) return size; - tmp_ret = microcode_ops->request_microcode_fw(bsp, µcode_pdev->dev, true); - if (tmp_ret != UCODE_NEW) - return size; - get_online_cpus(); ret = check_online_cpus(); if (ret) goto put; + tmp_ret = microcode_ops->request_microcode_fw(bsp, µcode_pdev->dev, true); + if (tmp_ret != UCODE_NEW) + goto put; + mutex_lock(µcode_mutex); ret = microcode_reload_late(); mutex_unlock(µcode_mutex); diff --git a/arch/x86/kernel/kprobes/core.c b/arch/x86/kernel/kprobes/core.c index dfc3ab44bc5d3..3334e14003457 100644 --- a/arch/x86/kernel/kprobes/core.c +++ b/arch/x86/kernel/kprobes/core.c @@ -170,6 +170,8 @@ NOKPROBE_SYMBOL(skip_prefixes); int can_boost(struct insn *insn, void *addr) { kprobe_opcode_t opcode; + insn_byte_t prefix; + int i; if (search_exception_tables((unsigned long)addr)) return 0; /* Page fault may occur on this address. */ @@ -182,9 +184,14 @@ int can_boost(struct insn *insn, void *addr) if (insn->opcode.nbytes != 1) return 0; - /* Can't boost Address-size override prefix */ - if (unlikely(inat_is_address_size_prefix(insn->attr))) - return 0; + for_each_insn_prefix(insn, i, prefix) { + insn_attr_t attr; + + attr = inat_get_opcode_attribute(prefix); + /* Can't boost Address-size override prefix and CS override prefix */ + if (prefix == 0x2e || inat_is_address_size_prefix(attr)) + return 0; + } opcode = insn->opcode.bytes[0]; @@ -209,8 +216,8 @@ int can_boost(struct insn *insn, void *addr) /* clear and set flags are boostable */ return (opcode == 0xf5 || (0xf7 < opcode && opcode < 0xfe)); default: - /* CS override prefix and call are not boostable */ - return (opcode != 0x2e && opcode != 0x9a); + /* call is not boostable */ + return opcode != 0x9a; } } diff --git a/arch/x86/kvm/x86.c b/arch/x86/kvm/x86.c index 8e4eef73531a5..435e74e1f2e54 100644 --- a/arch/x86/kvm/x86.c +++ b/arch/x86/kvm/x86.c @@ -6911,6 +6911,7 @@ void kvm_arch_exit(void) cpuhp_remove_state_nocalls(CPUHP_AP_X86_KVM_CLK_ONLINE); #ifdef CONFIG_X86_64 pvclock_gtod_unregister_notifier(&pvclock_gtod_notifier); + cancel_work_sync(&pvclock_gtod_work); #endif kvm_x86_ops = NULL; kvm_mmu_module_exit(); diff --git a/arch/x86/lib/msr-smp.c b/arch/x86/lib/msr-smp.c index fee8b9c0520c9..9009393f44c78 100644 --- a/arch/x86/lib/msr-smp.c +++ b/arch/x86/lib/msr-smp.c @@ -253,7 +253,7 @@ static void __wrmsr_safe_regs_on_cpu(void *info) rv->err = wrmsr_safe_regs(rv->regs); } -int rdmsr_safe_regs_on_cpu(unsigned int cpu, u32 *regs) +int rdmsr_safe_regs_on_cpu(unsigned int cpu, u32 regs[8]) { int err; struct msr_regs_info rv; @@ -266,7 +266,7 @@ int rdmsr_safe_regs_on_cpu(unsigned int cpu, u32 *regs) } EXPORT_SYMBOL(rdmsr_safe_regs_on_cpu); -int wrmsr_safe_regs_on_cpu(unsigned int cpu, u32 *regs) +int wrmsr_safe_regs_on_cpu(unsigned int cpu, u32 regs[8]) { int err; struct msr_regs_info rv; diff --git a/block/blk-mq.c b/block/blk-mq.c index 195526b93895e..ae70b4809bec4 100644 --- a/block/blk-mq.c +++ b/block/blk-mq.c @@ -2673,10 +2673,12 @@ EXPORT_SYMBOL(blk_mq_init_allocated_queue); /* tags can _not_ be used after returning from blk_mq_exit_queue */ void blk_mq_exit_queue(struct request_queue *q) { - struct blk_mq_tag_set *set = q->tag_set; + struct blk_mq_tag_set *set = q->tag_set; - blk_mq_del_queue_tag_set(q); + /* Checks hctx->flags & BLK_MQ_F_TAG_QUEUE_SHARED. */ blk_mq_exit_hw_queues(q, set, set->nr_hw_queues); + /* May clear BLK_MQ_F_TAG_QUEUE_SHARED in hctx->flags. */ + blk_mq_del_queue_tag_set(q); } /* Basically redo blk_mq_init_queue with queue frozen */ diff --git a/crypto/api.c b/crypto/api.c index 1909195b2c70b..5efd4d6e63125 100644 --- a/crypto/api.c +++ b/crypto/api.c @@ -571,7 +571,7 @@ void crypto_destroy_tfm(void *mem, struct crypto_tfm *tfm) { struct crypto_alg *alg; - if (unlikely(!mem)) + if (IS_ERR_OR_NULL(mem)) return; alg = tfm->__crt_alg; diff --git a/drivers/acpi/arm64/gtdt.c b/drivers/acpi/arm64/gtdt.c index 92f9edf9d11ed..c39b36c558d6f 100644 --- a/drivers/acpi/arm64/gtdt.c +++ b/drivers/acpi/arm64/gtdt.c @@ -332,7 +332,7 @@ static int __init gtdt_import_sbsa_gwdt(struct acpi_gtdt_watchdog *wd, int index) { struct platform_device *pdev; - int irq = map_gt_gsi(wd->timer_interrupt, wd->timer_flags); + int irq; /* * According to SBSA specification the size of refresh and control @@ -341,7 +341,7 @@ static int __init gtdt_import_sbsa_gwdt(struct acpi_gtdt_watchdog *wd, struct resource res[] = { DEFINE_RES_MEM(wd->control_frame_address, SZ_4K), DEFINE_RES_MEM(wd->refresh_frame_address, SZ_4K), - DEFINE_RES_IRQ(irq), + {}, }; int nr_res = ARRAY_SIZE(res); @@ -351,10 +351,11 @@ static int __init gtdt_import_sbsa_gwdt(struct acpi_gtdt_watchdog *wd, if (!(wd->refresh_frame_address && wd->control_frame_address)) { pr_err(FW_BUG "failed to get the Watchdog base address.\n"); - acpi_unregister_gsi(wd->timer_interrupt); return -EINVAL; } + irq = map_gt_gsi(wd->timer_interrupt, wd->timer_flags); + res[2] = (struct resource)DEFINE_RES_IRQ(irq); if (irq <= 0) { pr_warn("failed to map the Watchdog interrupt.\n"); nr_res--; @@ -367,7 +368,8 @@ static int __init gtdt_import_sbsa_gwdt(struct acpi_gtdt_watchdog *wd, */ pdev = platform_device_register_simple("sbsa-gwdt", index, res, nr_res); if (IS_ERR(pdev)) { - acpi_unregister_gsi(wd->timer_interrupt); + if (irq > 0) + acpi_unregister_gsi(wd->timer_interrupt); return PTR_ERR(pdev); } diff --git a/drivers/acpi/cppc_acpi.c b/drivers/acpi/cppc_acpi.c index 5c6ecbb666081..1b43f8ebfabea 100644 --- a/drivers/acpi/cppc_acpi.c +++ b/drivers/acpi/cppc_acpi.c @@ -122,23 +122,15 @@ static DEFINE_PER_CPU(struct cpc_desc *, cpc_desc_ptr); */ #define NUM_RETRIES 500ULL -struct cppc_attr { - struct attribute attr; - ssize_t (*show)(struct kobject *kobj, - struct attribute *attr, char *buf); - ssize_t (*store)(struct kobject *kobj, - struct attribute *attr, const char *c, ssize_t count); -}; - #define define_one_cppc_ro(_name) \ -static struct cppc_attr _name = \ +static struct kobj_attribute _name = \ __ATTR(_name, 0444, show_##_name, NULL) #define to_cpc_desc(a) container_of(a, struct cpc_desc, kobj) #define show_cppc_data(access_fn, struct_name, member_name) \ static ssize_t show_##member_name(struct kobject *kobj, \ - struct attribute *attr, char *buf) \ + struct kobj_attribute *attr, char *buf) \ { \ struct cpc_desc *cpc_ptr = to_cpc_desc(kobj); \ struct struct_name st_name = {0}; \ @@ -164,7 +156,7 @@ show_cppc_data(cppc_get_perf_ctrs, cppc_perf_fb_ctrs, reference_perf); show_cppc_data(cppc_get_perf_ctrs, cppc_perf_fb_ctrs, wraparound_time); static ssize_t show_feedback_ctrs(struct kobject *kobj, - struct attribute *attr, char *buf) + struct kobj_attribute *attr, char *buf) { struct cpc_desc *cpc_ptr = to_cpc_desc(kobj); struct cppc_perf_fb_ctrs fb_ctrs = {0}; diff --git a/drivers/acpi/custom_method.c b/drivers/acpi/custom_method.c index 222ea3f12f41e..613041870872b 100644 --- a/drivers/acpi/custom_method.c +++ b/drivers/acpi/custom_method.c @@ -37,6 +37,8 @@ static ssize_t cm_write(struct file *file, const char __user * user_buf, sizeof(struct acpi_table_header))) return -EFAULT; uncopied_bytes = max_size = table.length; + /* make sure the buf is not allocated */ + kfree(buf); buf = kzalloc(max_size, GFP_KERNEL); if (!buf) return -ENOMEM; @@ -50,6 +52,7 @@ static ssize_t cm_write(struct file *file, const char __user * user_buf, (*ppos + count < count) || (count > uncopied_bytes)) { kfree(buf); + buf = NULL; return -EINVAL; } @@ -71,7 +74,6 @@ static ssize_t cm_write(struct file *file, const char __user * user_buf, add_taint(TAINT_OVERRIDDEN_ACPI_TABLE, LOCKDEP_NOW_UNRELIABLE); } - kfree(buf); return count; } diff --git a/drivers/acpi/scan.c b/drivers/acpi/scan.c index d3c551bdc2dac..1e7e2c438acf0 100644 --- a/drivers/acpi/scan.c +++ b/drivers/acpi/scan.c @@ -705,6 +705,7 @@ int acpi_device_add(struct acpi_device *device, result = acpi_device_set_name(device, acpi_device_bus_id); if (result) { + kfree_const(acpi_device_bus_id->bus_id); kfree(acpi_device_bus_id); goto err_unlock; } diff --git a/drivers/ata/libahci_platform.c b/drivers/ata/libahci_platform.c index 522b543f718d8..6a55aac0c60fc 100644 --- a/drivers/ata/libahci_platform.c +++ b/drivers/ata/libahci_platform.c @@ -544,11 +544,13 @@ int ahci_platform_init_host(struct platform_device *pdev, int i, irq, n_ports, rc; irq = platform_get_irq(pdev, 0); - if (irq <= 0) { + if (irq < 0) { if (irq != -EPROBE_DEFER) dev_err(dev, "no irq\n"); return irq; } + if (!irq) + return -EINVAL; hpriv->irq = irq; diff --git a/drivers/ata/pata_arasan_cf.c b/drivers/ata/pata_arasan_cf.c index ebecab8c3f36c..7c1c399450f32 100644 --- a/drivers/ata/pata_arasan_cf.c +++ b/drivers/ata/pata_arasan_cf.c @@ -817,12 +817,19 @@ static int arasan_cf_probe(struct platform_device *pdev) else quirk = CF_BROKEN_UDMA; /* as it is on spear1340 */ - /* if irq is 0, support only PIO */ - acdev->irq = platform_get_irq(pdev, 0); - if (acdev->irq) + /* + * If there's an error getting IRQ (or we do get IRQ0), + * support only PIO + */ + ret = platform_get_irq(pdev, 0); + if (ret > 0) { + acdev->irq = ret; irq_handler = arasan_cf_interrupt; - else + } else if (ret == -EPROBE_DEFER) { + return ret; + } else { quirk |= CF_BROKEN_MWDMA | CF_BROKEN_UDMA; + } acdev->pbase = res->start; acdev->vbase = devm_ioremap_nocache(&pdev->dev, res->start, diff --git a/drivers/ata/pata_ixp4xx_cf.c b/drivers/ata/pata_ixp4xx_cf.c index 0b0d93065f5a1..867621f8c3873 100644 --- a/drivers/ata/pata_ixp4xx_cf.c +++ b/drivers/ata/pata_ixp4xx_cf.c @@ -169,8 +169,12 @@ static int ixp4xx_pata_probe(struct platform_device *pdev) return -ENOMEM; irq = platform_get_irq(pdev, 0); - if (irq) + if (irq > 0) irq_set_irq_type(irq, IRQ_TYPE_EDGE_RISING); + else if (irq < 0) + return irq; + else + return -EINVAL; /* Setup expansion bus chip selects */ *data->cs0_cfg = data->cs0_bits; diff --git a/drivers/ata/sata_mv.c b/drivers/ata/sata_mv.c index 2910b22fac117..57ef11ecbb9be 100644 --- a/drivers/ata/sata_mv.c +++ b/drivers/ata/sata_mv.c @@ -4110,6 +4110,10 @@ static int mv_platform_probe(struct platform_device *pdev) n_ports = mv_platform_data->n_ports; irq = platform_get_irq(pdev, 0); } + if (irq < 0) + return irq; + if (!irq) + return -EINVAL; host = ata_host_alloc_pinfo(&pdev->dev, ppi, n_ports); hpriv = devm_kzalloc(&pdev->dev, sizeof(*hpriv), GFP_KERNEL); diff --git a/drivers/base/regmap/regmap-debugfs.c b/drivers/base/regmap/regmap-debugfs.c index c9e5381a887bf..de706734b9214 100644 --- a/drivers/base/regmap/regmap-debugfs.c +++ b/drivers/base/regmap/regmap-debugfs.c @@ -665,6 +665,7 @@ void regmap_debugfs_exit(struct regmap *map) regmap_debugfs_free_dump_cache(map); mutex_unlock(&map->cache_lock); kfree(map->debugfs_name); + map->debugfs_name = NULL; } else { struct regmap_debugfs_node *node, *tmp; diff --git a/drivers/block/null_blk_zoned.c b/drivers/block/null_blk_zoned.c index 079ed33fd8067..ba018f1da5120 100644 --- a/drivers/block/null_blk_zoned.c +++ b/drivers/block/null_blk_zoned.c @@ -56,6 +56,7 @@ int null_zone_init(struct nullb_device *dev) void null_zone_exit(struct nullb_device *dev) { kvfree(dev->zones); + dev->zones = NULL; } static void null_zone_fill_bio(struct nullb_device *dev, struct bio *bio, diff --git a/drivers/bus/qcom-ebi2.c b/drivers/bus/qcom-ebi2.c index a6444244c4111..bfb67aa00becc 100644 --- a/drivers/bus/qcom-ebi2.c +++ b/drivers/bus/qcom-ebi2.c @@ -357,8 +357,10 @@ static int qcom_ebi2_probe(struct platform_device *pdev) /* Figure out the chipselect */ ret = of_property_read_u32(child, "reg", &csindex); - if (ret) + if (ret) { + of_node_put(child); return ret; + } if (csindex > 5) { dev_err(dev, diff --git a/drivers/char/tpm/eventlog/common.c b/drivers/char/tpm/eventlog/common.c index 7d70b654df04d..462476467bffe 100644 --- a/drivers/char/tpm/eventlog/common.c +++ b/drivers/char/tpm/eventlog/common.c @@ -112,6 +112,9 @@ void tpm_bios_log_setup(struct tpm_chip *chip) int log_version; int rc = 0; + if (chip->flags & TPM_CHIP_FLAG_VIRTUAL) + return; + rc = tpm_read_log(chip); if (rc < 0) return; diff --git a/drivers/char/tpm/tpm2-cmd.c b/drivers/char/tpm/tpm2-cmd.c index ef381caf5f43e..e71c6b24aed1c 100644 --- a/drivers/char/tpm/tpm2-cmd.c +++ b/drivers/char/tpm/tpm2-cmd.c @@ -960,6 +960,7 @@ static int tpm2_get_cc_attrs_tbl(struct tpm_chip *chip) if (nr_commands != be32_to_cpup((__be32 *)&buf.data[TPM_HEADER_SIZE + 5])) { + rc = -EFAULT; tpm_buf_destroy(&buf); goto out; } diff --git a/drivers/char/ttyprintk.c b/drivers/char/ttyprintk.c index 774748497aced..e56ac5adb5fcc 100644 --- a/drivers/char/ttyprintk.c +++ b/drivers/char/ttyprintk.c @@ -159,12 +159,23 @@ static int tpk_ioctl(struct tty_struct *tty, return 0; } +/* + * TTY operations hangup function. + */ +static void tpk_hangup(struct tty_struct *tty) +{ + struct ttyprintk_port *tpkp = tty->driver_data; + + tty_port_hangup(&tpkp->port); +} + static const struct tty_operations ttyprintk_ops = { .open = tpk_open, .close = tpk_close, .write = tpk_write, .write_room = tpk_write_room, .ioctl = tpk_ioctl, + .hangup = tpk_hangup, }; static const struct tty_port_operations null_ops = { }; diff --git a/drivers/clk/mvebu/armada-37xx-periph.c b/drivers/clk/mvebu/armada-37xx-periph.c index 499f5962c8b06..5d10733d6c041 100644 --- a/drivers/clk/mvebu/armada-37xx-periph.c +++ b/drivers/clk/mvebu/armada-37xx-periph.c @@ -74,6 +74,7 @@ struct clk_pm_cpu { void __iomem *reg_div; u8 shift_div; struct regmap *nb_pm_base; + unsigned long l1_expiration; }; #define to_clk_double_div(_hw) container_of(_hw, struct clk_double_div, hw) @@ -428,33 +429,6 @@ static u8 clk_pm_cpu_get_parent(struct clk_hw *hw) return val; } -static int clk_pm_cpu_set_parent(struct clk_hw *hw, u8 index) -{ - struct clk_pm_cpu *pm_cpu = to_clk_pm_cpu(hw); - struct regmap *base = pm_cpu->nb_pm_base; - int load_level; - - /* - * We set the clock parent only if the DVFS is available but - * not enabled. - */ - if (IS_ERR(base) || armada_3700_pm_dvfs_is_enabled(base)) - return -EINVAL; - - /* Set the parent clock for all the load level */ - for (load_level = 0; load_level < LOAD_LEVEL_NR; load_level++) { - unsigned int reg, mask, val, - offset = ARMADA_37XX_NB_TBG_SEL_OFF; - - armada_3700_pm_dvfs_update_regs(load_level, ®, &offset); - - val = index << offset; - mask = ARMADA_37XX_NB_TBG_SEL_MASK << offset; - regmap_update_bits(base, reg, mask, val); - } - return 0; -} - static unsigned long clk_pm_cpu_recalc_rate(struct clk_hw *hw, unsigned long parent_rate) { @@ -502,8 +476,10 @@ static long clk_pm_cpu_round_rate(struct clk_hw *hw, unsigned long rate, } /* - * Switching the CPU from the L2 or L3 frequencies (300 and 200 Mhz - * respectively) to L0 frequency (1.2 Ghz) requires a significant + * Workaround when base CPU frequnecy is 1000 or 1200 MHz + * + * Switching the CPU from the L2 or L3 frequencies (250/300 or 200 MHz + * respectively) to L0 frequency (1/1.2 GHz) requires a significant * amount of time to let VDD stabilize to the appropriate * voltage. This amount of time is large enough that it cannot be * covered by the hardware countdown register. Due to this, the CPU @@ -513,26 +489,56 @@ static long clk_pm_cpu_round_rate(struct clk_hw *hw, unsigned long rate, * To work around this problem, we prevent switching directly from the * L2/L3 frequencies to the L0 frequency, and instead switch to the L1 * frequency in-between. The sequence therefore becomes: - * 1. First switch from L2/L3(200/300MHz) to L1(600MHZ) + * 1. First switch from L2/L3 (200/250/300 MHz) to L1 (500/600 MHz) * 2. Sleep 20ms for stabling VDD voltage - * 3. Then switch from L1(600MHZ) to L0(1200Mhz). + * 3. Then switch from L1 (500/600 MHz) to L0 (1000/1200 MHz). */ -static void clk_pm_cpu_set_rate_wa(unsigned long rate, struct regmap *base) +static void clk_pm_cpu_set_rate_wa(struct clk_pm_cpu *pm_cpu, + unsigned int new_level, unsigned long rate, + struct regmap *base) { unsigned int cur_level; - if (rate != 1200 * 1000 * 1000) - return; - regmap_read(base, ARMADA_37XX_NB_CPU_LOAD, &cur_level); cur_level &= ARMADA_37XX_NB_CPU_LOAD_MASK; - if (cur_level <= ARMADA_37XX_DVFS_LOAD_1) + + if (cur_level == new_level) + return; + + /* + * System wants to go to L1 on its own. If we are going from L2/L3, + * remember when 20ms will expire. If from L0, set the value so that + * next switch to L0 won't have to wait. + */ + if (new_level == ARMADA_37XX_DVFS_LOAD_1) { + if (cur_level == ARMADA_37XX_DVFS_LOAD_0) + pm_cpu->l1_expiration = jiffies; + else + pm_cpu->l1_expiration = jiffies + msecs_to_jiffies(20); return; + } + + /* + * If we are setting to L2/L3, just invalidate L1 expiration time, + * sleeping is not needed. + */ + if (rate < 1000*1000*1000) + goto invalidate_l1_exp; + + /* + * We are going to L0 with rate >= 1GHz. Check whether we have been at + * L1 for long enough time. If not, go to L1 for 20ms. + */ + if (pm_cpu->l1_expiration && jiffies >= pm_cpu->l1_expiration) + goto invalidate_l1_exp; regmap_update_bits(base, ARMADA_37XX_NB_CPU_LOAD, ARMADA_37XX_NB_CPU_LOAD_MASK, ARMADA_37XX_DVFS_LOAD_1); msleep(20); + +invalidate_l1_exp: + pm_cpu->l1_expiration = 0; } static int clk_pm_cpu_set_rate(struct clk_hw *hw, unsigned long rate, @@ -566,7 +572,9 @@ static int clk_pm_cpu_set_rate(struct clk_hw *hw, unsigned long rate, reg = ARMADA_37XX_NB_CPU_LOAD; mask = ARMADA_37XX_NB_CPU_LOAD_MASK; - clk_pm_cpu_set_rate_wa(rate, base); + /* Apply workaround when base CPU frequency is 1000 or 1200 MHz */ + if (parent_rate >= 1000*1000*1000) + clk_pm_cpu_set_rate_wa(pm_cpu, load_level, rate, base); regmap_update_bits(base, reg, mask, load_level); @@ -580,7 +588,6 @@ static int clk_pm_cpu_set_rate(struct clk_hw *hw, unsigned long rate, static const struct clk_ops clk_pm_cpu_ops = { .get_parent = clk_pm_cpu_get_parent, - .set_parent = clk_pm_cpu_set_parent, .round_rate = clk_pm_cpu_round_rate, .set_rate = clk_pm_cpu_set_rate, .recalc_rate = clk_pm_cpu_recalc_rate, diff --git a/drivers/clk/qcom/a53-pll.c b/drivers/clk/qcom/a53-pll.c index 45cfc57bff924..af6ac17c7daeb 100644 --- a/drivers/clk/qcom/a53-pll.c +++ b/drivers/clk/qcom/a53-pll.c @@ -93,6 +93,7 @@ static const struct of_device_id qcom_a53pll_match_table[] = { { .compatible = "qcom,msm8916-a53pll" }, { } }; +MODULE_DEVICE_TABLE(of, qcom_a53pll_match_table); static struct platform_driver qcom_a53pll_driver = { .probe = qcom_a53pll_probe, diff --git a/drivers/clk/samsung/clk-exynos7.c b/drivers/clk/samsung/clk-exynos7.c index 492d516910800..9b02980ee929b 100644 --- a/drivers/clk/samsung/clk-exynos7.c +++ b/drivers/clk/samsung/clk-exynos7.c @@ -541,8 +541,13 @@ static const struct samsung_gate_clock top1_gate_clks[] __initconst = { GATE(CLK_ACLK_FSYS0_200, "aclk_fsys0_200", "dout_aclk_fsys0_200", ENABLE_ACLK_TOP13, 28, CLK_SET_RATE_PARENT | CLK_IS_CRITICAL, 0), + /* + * This clock is required for the CMU_FSYS1 registers access, keep it + * enabled permanently until proper runtime PM support is added. + */ GATE(CLK_ACLK_FSYS1_200, "aclk_fsys1_200", "dout_aclk_fsys1_200", - ENABLE_ACLK_TOP13, 24, CLK_SET_RATE_PARENT, 0), + ENABLE_ACLK_TOP13, 24, CLK_SET_RATE_PARENT | + CLK_IS_CRITICAL, 0), GATE(CLK_SCLK_PHY_FSYS1_26M, "sclk_phy_fsys1_26m", "dout_sclk_phy_fsys1_26m", ENABLE_SCLK_TOP1_FSYS11, diff --git a/drivers/clk/socfpga/clk-gate-a10.c b/drivers/clk/socfpga/clk-gate-a10.c index 36376c542055c..637e26babf898 100644 --- a/drivers/clk/socfpga/clk-gate-a10.c +++ b/drivers/clk/socfpga/clk-gate-a10.c @@ -157,6 +157,7 @@ static void __init __socfpga_gate_init(struct device_node *node, if (IS_ERR(socfpga_clk->sys_mgr_base_addr)) { pr_err("%s: failed to find altr,sys-mgr regmap!\n", __func__); + kfree(socfpga_clk); return; } } diff --git a/drivers/clk/uniphier/clk-uniphier-mux.c b/drivers/clk/uniphier/clk-uniphier-mux.c index 2c243a894f3b9..3a52ab968ac24 100644 --- a/drivers/clk/uniphier/clk-uniphier-mux.c +++ b/drivers/clk/uniphier/clk-uniphier-mux.c @@ -40,10 +40,10 @@ static int uniphier_clk_mux_set_parent(struct clk_hw *hw, u8 index) static u8 uniphier_clk_mux_get_parent(struct clk_hw *hw) { struct uniphier_clk_mux *mux = to_uniphier_clk_mux(hw); - int num_parents = clk_hw_get_num_parents(hw); + unsigned int num_parents = clk_hw_get_num_parents(hw); int ret; unsigned int val; - u8 i; + unsigned int i; ret = regmap_read(mux->regmap, mux->reg, &val); if (ret) diff --git a/drivers/cpufreq/armada-37xx-cpufreq.c b/drivers/cpufreq/armada-37xx-cpufreq.c index 9b0b490d70ff4..a36452bd9612d 100644 --- a/drivers/cpufreq/armada-37xx-cpufreq.c +++ b/drivers/cpufreq/armada-37xx-cpufreq.c @@ -25,6 +25,10 @@ #include "cpufreq-dt.h" +/* Clk register set */ +#define ARMADA_37XX_CLK_TBG_SEL 0 +#define ARMADA_37XX_CLK_TBG_SEL_CPU_OFF 22 + /* Power management in North Bridge register set */ #define ARMADA_37XX_NB_L0L1 0x18 #define ARMADA_37XX_NB_L2L3 0x1C @@ -69,6 +73,8 @@ #define LOAD_LEVEL_NR 4 #define MIN_VOLT_MV 1000 +#define MIN_VOLT_MV_FOR_L1_1000MHZ 1108 +#define MIN_VOLT_MV_FOR_L1_1200MHZ 1155 /* AVS value for the corresponding voltage (in mV) */ static int avs_map[] = { @@ -120,10 +126,15 @@ static struct armada_37xx_dvfs *armada_37xx_cpu_freq_info_get(u32 freq) * will be configured then the DVFS will be enabled. */ static void __init armada37xx_cpufreq_dvfs_setup(struct regmap *base, - struct clk *clk, u8 *divider) + struct regmap *clk_base, u8 *divider) { + u32 cpu_tbg_sel; int load_lvl; - struct clk *parent; + + /* Determine to which TBG clock is CPU connected */ + regmap_read(clk_base, ARMADA_37XX_CLK_TBG_SEL, &cpu_tbg_sel); + cpu_tbg_sel >>= ARMADA_37XX_CLK_TBG_SEL_CPU_OFF; + cpu_tbg_sel &= ARMADA_37XX_NB_TBG_SEL_MASK; for (load_lvl = 0; load_lvl < LOAD_LEVEL_NR; load_lvl++) { unsigned int reg, mask, val, offset = 0; @@ -142,6 +153,11 @@ static void __init armada37xx_cpufreq_dvfs_setup(struct regmap *base, mask = (ARMADA_37XX_NB_CLK_SEL_MASK << ARMADA_37XX_NB_CLK_SEL_OFF); + /* Set TBG index, for all levels we use the same TBG */ + val = cpu_tbg_sel << ARMADA_37XX_NB_TBG_SEL_OFF; + mask = (ARMADA_37XX_NB_TBG_SEL_MASK + << ARMADA_37XX_NB_TBG_SEL_OFF); + /* * Set cpu divider based on the pre-computed array in * order to have balanced step. @@ -160,14 +176,6 @@ static void __init armada37xx_cpufreq_dvfs_setup(struct regmap *base, regmap_update_bits(base, reg, mask, val); } - - /* - * Set cpu clock source, for all the level we keep the same - * clock source that the one already configured. For this one - * we need to use the clock framework - */ - parent = clk_get_parent(clk); - clk_set_parent(clk, parent); } /* @@ -202,6 +210,8 @@ static u32 armada_37xx_avs_val_match(int target_vm) * - L2 & L3 voltage should be about 150mv smaller than L0 voltage. * This function calculates L1 & L2 & L3 AVS values dynamically based * on L0 voltage and fill all AVS values to the AVS value table. + * When base CPU frequency is 1000 or 1200 MHz then there is additional + * minimal avs value for load L1. */ static void __init armada37xx_cpufreq_avs_configure(struct regmap *base, struct armada_37xx_dvfs *dvfs) @@ -233,6 +243,19 @@ static void __init armada37xx_cpufreq_avs_configure(struct regmap *base, for (load_level = 1; load_level < LOAD_LEVEL_NR; load_level++) dvfs->avs[load_level] = avs_min; + /* + * Set the avs values for load L0 and L1 when base CPU frequency + * is 1000/1200 MHz to its typical initial values according to + * the Armada 3700 Hardware Specifications. + */ + if (dvfs->cpu_freq_max >= 1000*1000*1000) { + if (dvfs->cpu_freq_max >= 1200*1000*1000) + avs_min = armada_37xx_avs_val_match(MIN_VOLT_MV_FOR_L1_1200MHZ); + else + avs_min = armada_37xx_avs_val_match(MIN_VOLT_MV_FOR_L1_1000MHZ); + dvfs->avs[0] = dvfs->avs[1] = avs_min; + } + return; } @@ -252,6 +275,26 @@ static void __init armada37xx_cpufreq_avs_configure(struct regmap *base, target_vm = avs_map[l0_vdd_min] - 150; target_vm = target_vm > MIN_VOLT_MV ? target_vm : MIN_VOLT_MV; dvfs->avs[2] = dvfs->avs[3] = armada_37xx_avs_val_match(target_vm); + + /* + * Fix the avs value for load L1 when base CPU frequency is 1000/1200 MHz, + * otherwise the CPU gets stuck when switching from load L1 to load L0. + * Also ensure that avs value for load L1 is not higher than for L0. + */ + if (dvfs->cpu_freq_max >= 1000*1000*1000) { + u32 avs_min_l1; + + if (dvfs->cpu_freq_max >= 1200*1000*1000) + avs_min_l1 = armada_37xx_avs_val_match(MIN_VOLT_MV_FOR_L1_1200MHZ); + else + avs_min_l1 = armada_37xx_avs_val_match(MIN_VOLT_MV_FOR_L1_1000MHZ); + + if (avs_min_l1 > dvfs->avs[0]) + avs_min_l1 = dvfs->avs[0]; + + if (dvfs->avs[1] < avs_min_l1) + dvfs->avs[1] = avs_min_l1; + } } static void __init armada37xx_cpufreq_avs_setup(struct regmap *base, @@ -360,11 +403,16 @@ static int __init armada37xx_cpufreq_driver_init(void) struct platform_device *pdev; unsigned long freq; unsigned int cur_frequency, base_frequency; - struct regmap *nb_pm_base, *avs_base; + struct regmap *nb_clk_base, *nb_pm_base, *avs_base; struct device *cpu_dev; int load_lvl, ret; struct clk *clk, *parent; + nb_clk_base = + syscon_regmap_lookup_by_compatible("marvell,armada-3700-periph-clock-nb"); + if (IS_ERR(nb_clk_base)) + return -ENODEV; + nb_pm_base = syscon_regmap_lookup_by_compatible("marvell,armada-3700-nb-pm"); @@ -423,7 +471,7 @@ static int __init armada37xx_cpufreq_driver_init(void) return -EINVAL; } - dvfs = armada_37xx_cpu_freq_info_get(cur_frequency); + dvfs = armada_37xx_cpu_freq_info_get(base_frequency); if (!dvfs) { clk_put(clk); return -EINVAL; @@ -441,7 +489,7 @@ static int __init armada37xx_cpufreq_driver_init(void) armada37xx_cpufreq_avs_configure(avs_base, dvfs); armada37xx_cpufreq_avs_setup(avs_base, dvfs); - armada37xx_cpufreq_dvfs_setup(nb_pm_base, clk, dvfs->divider); + armada37xx_cpufreq_dvfs_setup(nb_pm_base, nb_clk_base, dvfs->divider); clk_put(clk); for (load_lvl = ARMADA_37XX_DVFS_LOAD_0; load_lvl < LOAD_LEVEL_NR; @@ -475,7 +523,7 @@ disable_dvfs: remove_opp: /* clean-up the already added opp before leaving */ while (load_lvl-- > ARMADA_37XX_DVFS_LOAD_0) { - freq = cur_frequency / dvfs->divider[load_lvl]; + freq = base_frequency / dvfs->divider[load_lvl]; dev_pm_opp_remove(cpu_dev, freq); } diff --git a/drivers/crypto/qat/qat_c3xxxvf/adf_drv.c b/drivers/crypto/qat/qat_c3xxxvf/adf_drv.c index 613c7d5644ced..e87b7c466bdbf 100644 --- a/drivers/crypto/qat/qat_c3xxxvf/adf_drv.c +++ b/drivers/crypto/qat/qat_c3xxxvf/adf_drv.c @@ -238,12 +238,12 @@ static int adf_probe(struct pci_dev *pdev, const struct pci_device_id *ent) if (ret) goto out_err_free_reg; - set_bit(ADF_STATUS_PF_RUNNING, &accel_dev->status); - ret = adf_dev_init(accel_dev); if (ret) goto out_err_dev_shutdown; + set_bit(ADF_STATUS_PF_RUNNING, &accel_dev->status); + ret = adf_dev_start(accel_dev); if (ret) goto out_err_dev_stop; diff --git a/drivers/crypto/qat/qat_c62xvf/adf_drv.c b/drivers/crypto/qat/qat_c62xvf/adf_drv.c index 278452b8ef81c..a8f3f2ecae70d 100644 --- a/drivers/crypto/qat/qat_c62xvf/adf_drv.c +++ b/drivers/crypto/qat/qat_c62xvf/adf_drv.c @@ -238,12 +238,12 @@ static int adf_probe(struct pci_dev *pdev, const struct pci_device_id *ent) if (ret) goto out_err_free_reg; - set_bit(ADF_STATUS_PF_RUNNING, &accel_dev->status); - ret = adf_dev_init(accel_dev); if (ret) goto out_err_dev_shutdown; + set_bit(ADF_STATUS_PF_RUNNING, &accel_dev->status); + ret = adf_dev_start(accel_dev); if (ret) goto out_err_dev_stop; diff --git a/drivers/crypto/qat/qat_common/adf_isr.c b/drivers/crypto/qat/qat_common/adf_isr.c index cd1cdf5305bc9..4898ef41fd9fd 100644 --- a/drivers/crypto/qat/qat_common/adf_isr.c +++ b/drivers/crypto/qat/qat_common/adf_isr.c @@ -330,19 +330,32 @@ int adf_isr_resource_alloc(struct adf_accel_dev *accel_dev) ret = adf_isr_alloc_msix_entry_table(accel_dev); if (ret) - return ret; - if (adf_enable_msix(accel_dev)) goto err_out; - if (adf_setup_bh(accel_dev)) - goto err_out; + ret = adf_enable_msix(accel_dev); + if (ret) + goto err_free_msix_table; - if (adf_request_irqs(accel_dev)) - goto err_out; + ret = adf_setup_bh(accel_dev); + if (ret) + goto err_disable_msix; + + ret = adf_request_irqs(accel_dev); + if (ret) + goto err_cleanup_bh; return 0; + +err_cleanup_bh: + adf_cleanup_bh(accel_dev); + +err_disable_msix: + adf_disable_msix(&accel_dev->accel_pci_dev); + +err_free_msix_table: + adf_isr_free_msix_entry_table(accel_dev); + err_out: - adf_isr_resource_free(accel_dev); - return -EFAULT; + return ret; } EXPORT_SYMBOL_GPL(adf_isr_resource_alloc); diff --git a/drivers/crypto/qat/qat_common/adf_transport.c b/drivers/crypto/qat/qat_common/adf_transport.c index 57d2622728a57..4c0067f8c079f 100644 --- a/drivers/crypto/qat/qat_common/adf_transport.c +++ b/drivers/crypto/qat/qat_common/adf_transport.c @@ -197,6 +197,7 @@ static int adf_init_ring(struct adf_etr_ring_data *ring) dev_err(&GET_DEV(accel_dev), "Ring address not aligned\n"); dma_free_coherent(&GET_DEV(accel_dev), ring_size_bytes, ring->base_addr, ring->dma_addr); + ring->base_addr = NULL; return -EFAULT; } diff --git a/drivers/crypto/qat/qat_common/adf_vf_isr.c b/drivers/crypto/qat/qat_common/adf_vf_isr.c index 4a73fc70f7a97..df9a1f35b8320 100644 --- a/drivers/crypto/qat/qat_common/adf_vf_isr.c +++ b/drivers/crypto/qat/qat_common/adf_vf_isr.c @@ -304,17 +304,26 @@ int adf_vf_isr_resource_alloc(struct adf_accel_dev *accel_dev) goto err_out; if (adf_setup_pf2vf_bh(accel_dev)) - goto err_out; + goto err_disable_msi; if (adf_setup_bh(accel_dev)) - goto err_out; + goto err_cleanup_pf2vf_bh; if (adf_request_msi_irq(accel_dev)) - goto err_out; + goto err_cleanup_bh; return 0; + +err_cleanup_bh: + adf_cleanup_bh(accel_dev); + +err_cleanup_pf2vf_bh: + adf_cleanup_pf2vf_bh(accel_dev); + +err_disable_msi: + adf_disable_msi(accel_dev); + err_out: - adf_vf_isr_resource_free(accel_dev); return -EFAULT; } EXPORT_SYMBOL_GPL(adf_vf_isr_resource_alloc); diff --git a/drivers/crypto/qat/qat_dh895xccvf/adf_drv.c b/drivers/crypto/qat/qat_dh895xccvf/adf_drv.c index 3da0f951cb590..1b954abf67fb8 100644 --- a/drivers/crypto/qat/qat_dh895xccvf/adf_drv.c +++ b/drivers/crypto/qat/qat_dh895xccvf/adf_drv.c @@ -238,12 +238,12 @@ static int adf_probe(struct pci_dev *pdev, const struct pci_device_id *ent) if (ret) goto out_err_free_reg; - set_bit(ADF_STATUS_PF_RUNNING, &accel_dev->status); - ret = adf_dev_init(accel_dev); if (ret) goto out_err_dev_shutdown; + set_bit(ADF_STATUS_PF_RUNNING, &accel_dev->status); + ret = adf_dev_start(accel_dev); if (ret) goto out_err_dev_stop; diff --git a/drivers/extcon/extcon-arizona.c b/drivers/extcon/extcon-arizona.c index 9327479c719c2..c857120c00d94 100644 --- a/drivers/extcon/extcon-arizona.c +++ b/drivers/extcon/extcon-arizona.c @@ -602,7 +602,7 @@ static irqreturn_t arizona_hpdet_irq(int irq, void *data) struct arizona *arizona = info->arizona; int id_gpio = arizona->pdata.hpdet_id_gpio; unsigned int report = EXTCON_JACK_HEADPHONE; - int ret, reading; + int ret, reading, state; bool mic = false; mutex_lock(&info->lock); @@ -615,12 +615,11 @@ static irqreturn_t arizona_hpdet_irq(int irq, void *data) } /* If the cable was removed while measuring ignore the result */ - ret = extcon_get_state(info->edev, EXTCON_MECHANICAL); - if (ret < 0) { - dev_err(arizona->dev, "Failed to check cable state: %d\n", - ret); + state = extcon_get_state(info->edev, EXTCON_MECHANICAL); + if (state < 0) { + dev_err(arizona->dev, "Failed to check cable state: %d\n", state); goto out; - } else if (!ret) { + } else if (!state) { dev_dbg(arizona->dev, "Ignoring HPDET for removed cable\n"); goto done; } @@ -673,7 +672,7 @@ done: ARIZONA_ACCDET_MODE_MASK, ARIZONA_ACCDET_MODE_MIC); /* If we have a mic then reenable MICDET */ - if (mic || info->mic) + if (state && (mic || info->mic)) arizona_start_mic(info); if (info->hpdet_active) { @@ -681,7 +680,9 @@ done: info->hpdet_active = false; } - info->hpdet_done = true; + /* Do not set hp_det done when the cable has been unplugged */ + if (state) + info->hpdet_done = true; out: mutex_unlock(&info->lock); diff --git a/drivers/firmware/Kconfig b/drivers/firmware/Kconfig index ed212c8b41083..1c419e4cea839 100644 --- a/drivers/firmware/Kconfig +++ b/drivers/firmware/Kconfig @@ -248,6 +248,7 @@ config FW_CFG_SYSFS_CMDLINE config QCOM_SCM bool depends on ARM || ARM64 + depends on HAVE_ARM_SMCCC select RESET_CONTROLLER config QCOM_SCM_32 diff --git a/drivers/gpio/gpiolib-acpi.c b/drivers/gpio/gpiolib-acpi.c index 4ad34c6803ade..b018909a4e46c 100644 --- a/drivers/gpio/gpiolib-acpi.c +++ b/drivers/gpio/gpiolib-acpi.c @@ -1355,6 +1355,20 @@ static const struct dmi_system_id gpiolib_acpi_quirks[] = { .no_edge_events_on_boot = true, }, }, + { + /* + * The Dell Venue 10 Pro 5055, with Bay Trail SoC + TI PMIC uses an + * external embedded-controller connected via I2C + an ACPI GPIO + * event handler on INT33FFC:02 pin 12, causing spurious wakeups. + */ + .matches = { + DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), + DMI_MATCH(DMI_PRODUCT_NAME, "Venue 10 Pro 5055"), + }, + .driver_data = &(struct acpi_gpiolib_dmi_quirk) { + .ignore_wake = "INT33FC:02@12", + }, + }, { /* * HP X2 10 models with Cherry Trail SoC + TI PMIC use an diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c index 1abf5b5bac9e5..18402a6ba8fe3 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_irq.c @@ -447,7 +447,7 @@ void amdgpu_irq_gpu_reset_resume_helper(struct amdgpu_device *adev) for (j = 0; j < AMDGPU_MAX_IRQ_SRC_ID; ++j) { struct amdgpu_irq_src *src = adev->irq.client[i].sources[j]; - if (!src) + if (!src || !src->funcs || !src->funcs->set) continue; for (k = 0; k < src->num_types; k++) amdgpu_irq_update(adev, src, k); diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c index abad7460084f2..757fa486aac41 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_ttm.c @@ -971,7 +971,7 @@ static void amdgpu_ttm_tt_unpin_userptr(struct ttm_tt *ttm) DMA_BIDIRECTIONAL : DMA_TO_DEVICE; /* double check that we don't free the table twice */ - if (!ttm->sg->sgl) + if (!ttm->sg || !ttm->sg->sgl) return; /* unmap the pages mapped to the device */ diff --git a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c index e5a6db6beab7a..8c5f39beee7cf 100644 --- a/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c +++ b/drivers/gpu/drm/amd/amdgpu/amdgpu_uvd.c @@ -231,7 +231,7 @@ int amdgpu_uvd_sw_init(struct amdgpu_device *adev) if ((adev->asic_type == CHIP_POLARIS10 || adev->asic_type == CHIP_POLARIS11) && (adev->uvd.fw_version < FW_1_66_16)) - DRM_ERROR("POLARIS10/11 UVD firmware version %hu.%hu is too old.\n", + DRM_ERROR("POLARIS10/11 UVD firmware version %u.%u is too old.\n", version_major, version_minor); } else { unsigned int enc_major, enc_minor, dec_minor; diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_iommu.c b/drivers/gpu/drm/amd/amdkfd/kfd_iommu.c index 01494752c36a8..f3a526ed8059d 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_iommu.c +++ b/drivers/gpu/drm/amd/amdkfd/kfd_iommu.c @@ -20,6 +20,10 @@ * OTHER DEALINGS IN THE SOFTWARE. */ +#include + +#if IS_REACHABLE(CONFIG_AMD_IOMMU_V2) + #include #include #include @@ -366,3 +370,5 @@ int kfd_iommu_add_perf_counters(struct kfd_topology_device *kdev) return 0; } + +#endif diff --git a/drivers/gpu/drm/amd/amdkfd/kfd_iommu.h b/drivers/gpu/drm/amd/amdkfd/kfd_iommu.h index dd23d9fdf6a82..afd420b01a0c2 100644 --- a/drivers/gpu/drm/amd/amdkfd/kfd_iommu.h +++ b/drivers/gpu/drm/amd/amdkfd/kfd_iommu.h @@ -23,7 +23,9 @@ #ifndef __KFD_IOMMU_H__ #define __KFD_IOMMU_H__ -#if defined(CONFIG_AMD_IOMMU_V2_MODULE) || defined(CONFIG_AMD_IOMMU_V2) +#include + +#if IS_REACHABLE(CONFIG_AMD_IOMMU_V2) #define KFD_SUPPORT_IOMMU_V2 @@ -46,6 +48,9 @@ static inline int kfd_iommu_check_device(struct kfd_dev *kfd) } static inline int kfd_iommu_device_init(struct kfd_dev *kfd) { +#if IS_MODULE(CONFIG_AMD_IOMMU_V2) + WARN_ONCE(1, "iommu_v2 module is not usable by built-in KFD"); +#endif return 0; } @@ -73,6 +78,6 @@ static inline int kfd_iommu_add_perf_counters(struct kfd_topology_device *kdev) return 0; } -#endif /* defined(CONFIG_AMD_IOMMU_V2) */ +#endif /* IS_REACHABLE(CONFIG_AMD_IOMMU_V2) */ #endif /* __KFD_IOMMU_H__ */ diff --git a/drivers/gpu/drm/i915/gvt/gvt.c b/drivers/gpu/drm/i915/gvt/gvt.c index 46c8b720e3363..3e3876d141cef 100644 --- a/drivers/gpu/drm/i915/gvt/gvt.c +++ b/drivers/gpu/drm/i915/gvt/gvt.c @@ -128,7 +128,7 @@ static bool intel_get_gvt_attrs(struct attribute ***type_attrs, return true; } -static bool intel_gvt_init_vgpu_type_groups(struct intel_gvt *gvt) +static int intel_gvt_init_vgpu_type_groups(struct intel_gvt *gvt) { int i, j; struct intel_vgpu_type *type; @@ -146,7 +146,7 @@ static bool intel_gvt_init_vgpu_type_groups(struct intel_gvt *gvt) gvt_vgpu_type_groups[i] = group; } - return true; + return 0; unwind: for (j = 0; j < i; j++) { @@ -154,7 +154,7 @@ unwind: kfree(group); } - return false; + return -ENOMEM; } static void intel_gvt_cleanup_vgpu_type_groups(struct intel_gvt *gvt) @@ -416,7 +416,7 @@ int intel_gvt_init_device(struct drm_i915_private *dev_priv) goto out_clean_thread; ret = intel_gvt_init_vgpu_type_groups(gvt); - if (ret == false) { + if (ret) { gvt_err("failed to init vgpu type groups: %d\n", ret); goto out_clean_types; } diff --git a/drivers/gpu/drm/i915/intel_pm.c b/drivers/gpu/drm/i915/intel_pm.c index 8d731eb1de69c..aa8d2aca0f02f 100644 --- a/drivers/gpu/drm/i915/intel_pm.c +++ b/drivers/gpu/drm/i915/intel_pm.c @@ -2951,7 +2951,7 @@ int ilk_wm_max_level(const struct drm_i915_private *dev_priv) static void intel_print_wm_latency(struct drm_i915_private *dev_priv, const char *name, - const uint16_t wm[8]) + const uint16_t wm[]) { int level, max_level = ilk_wm_max_level(dev_priv); diff --git a/drivers/gpu/drm/msm/disp/mdp5/mdp5_cmd_encoder.c b/drivers/gpu/drm/msm/disp/mdp5/mdp5_cmd_encoder.c index d6f79dc755b46..14e2ce87bab10 100644 --- a/drivers/gpu/drm/msm/disp/mdp5/mdp5_cmd_encoder.c +++ b/drivers/gpu/drm/msm/disp/mdp5/mdp5_cmd_encoder.c @@ -78,9 +78,17 @@ static int pingpong_tearcheck_setup(struct drm_encoder *encoder, | MDP5_PP_SYNC_CONFIG_VSYNC_IN_EN; cfg |= MDP5_PP_SYNC_CONFIG_VSYNC_COUNT(vclks_line); + /* + * Tearcheck emits a blanking signal every vclks_line * vtotal * 2 ticks on + * the vsync_clk equating to roughly half the desired panel refresh rate. + * This is only necessary as stability fallback if interrupts from the + * panel arrive too late or not at all, but is currently used by default + * because these panel interrupts are not wired up yet. + */ mdp5_write(mdp5_kms, REG_MDP5_PP_SYNC_CONFIG_VSYNC(pp_id), cfg); mdp5_write(mdp5_kms, - REG_MDP5_PP_SYNC_CONFIG_HEIGHT(pp_id), 0xfff0); + REG_MDP5_PP_SYNC_CONFIG_HEIGHT(pp_id), (2 * mode->vtotal)); + mdp5_write(mdp5_kms, REG_MDP5_PP_VSYNC_INIT_VAL(pp_id), mode->vdisplay); mdp5_write(mdp5_kms, REG_MDP5_PP_RD_PTR_IRQ(pp_id), mode->vdisplay + 1); diff --git a/drivers/gpu/drm/radeon/radeon.h b/drivers/gpu/drm/radeon/radeon.h index 1a6f6edb35151..62e6e3b73e4e6 100644 --- a/drivers/gpu/drm/radeon/radeon.h +++ b/drivers/gpu/drm/radeon/radeon.h @@ -1558,6 +1558,7 @@ struct radeon_dpm { void *priv; u32 new_active_crtcs; int new_active_crtc_count; + int high_pixelclock_count; u32 current_active_crtcs; int current_active_crtc_count; bool single_display; diff --git a/drivers/gpu/drm/radeon/radeon_atombios.c b/drivers/gpu/drm/radeon/radeon_atombios.c index f422a8d6aec40..821b03d6142b0 100644 --- a/drivers/gpu/drm/radeon/radeon_atombios.c +++ b/drivers/gpu/drm/radeon/radeon_atombios.c @@ -2133,11 +2133,14 @@ static int radeon_atombios_parse_power_table_1_3(struct radeon_device *rdev) return state_index; /* last mode is usually default, array is low to high */ for (i = 0; i < num_modes; i++) { - rdev->pm.power_state[state_index].clock_info = - kcalloc(1, sizeof(struct radeon_pm_clock_info), - GFP_KERNEL); + /* avoid memory leaks from invalid modes or unknown frev. */ + if (!rdev->pm.power_state[state_index].clock_info) { + rdev->pm.power_state[state_index].clock_info = + kzalloc(sizeof(struct radeon_pm_clock_info), + GFP_KERNEL); + } if (!rdev->pm.power_state[state_index].clock_info) - return state_index; + goto out; rdev->pm.power_state[state_index].num_clock_modes = 1; rdev->pm.power_state[state_index].clock_info[0].voltage.type = VOLTAGE_NONE; switch (frev) { @@ -2256,17 +2259,24 @@ static int radeon_atombios_parse_power_table_1_3(struct radeon_device *rdev) break; } } +out: + /* free any unused clock_info allocation. */ + if (state_index && state_index < num_modes) { + kfree(rdev->pm.power_state[state_index].clock_info); + rdev->pm.power_state[state_index].clock_info = NULL; + } + /* last mode is usually default */ - if (rdev->pm.default_power_state_index == -1) { + if (state_index && rdev->pm.default_power_state_index == -1) { rdev->pm.power_state[state_index - 1].type = POWER_STATE_TYPE_DEFAULT; rdev->pm.default_power_state_index = state_index - 1; rdev->pm.power_state[state_index - 1].default_clock_mode = &rdev->pm.power_state[state_index - 1].clock_info[0]; - rdev->pm.power_state[state_index].flags &= + rdev->pm.power_state[state_index - 1].flags &= ~RADEON_PM_STATE_SINGLE_DISPLAY_ONLY; - rdev->pm.power_state[state_index].misc = 0; - rdev->pm.power_state[state_index].misc2 = 0; + rdev->pm.power_state[state_index - 1].misc = 0; + rdev->pm.power_state[state_index - 1].misc2 = 0; } return state_index; } diff --git a/drivers/gpu/drm/radeon/radeon_kms.c b/drivers/gpu/drm/radeon/radeon_kms.c index 34b3cb6c146f9..3f75b4be7fa4a 100644 --- a/drivers/gpu/drm/radeon/radeon_kms.c +++ b/drivers/gpu/drm/radeon/radeon_kms.c @@ -501,6 +501,7 @@ static int radeon_info_ioctl(struct drm_device *dev, void *data, struct drm_file *value = rdev->config.si.backend_enable_mask; } else { DRM_DEBUG_KMS("BACKEND_ENABLED_MASK is si+ only!\n"); + return -EINVAL; } break; case RADEON_INFO_MAX_SCLK: diff --git a/drivers/gpu/drm/radeon/radeon_pm.c b/drivers/gpu/drm/radeon/radeon_pm.c index 4b6542538ff91..c213a5c9227ed 100644 --- a/drivers/gpu/drm/radeon/radeon_pm.c +++ b/drivers/gpu/drm/radeon/radeon_pm.c @@ -1715,6 +1715,7 @@ static void radeon_pm_compute_clocks_dpm(struct radeon_device *rdev) struct drm_device *ddev = rdev->ddev; struct drm_crtc *crtc; struct radeon_crtc *radeon_crtc; + struct radeon_connector *radeon_connector; if (!rdev->pm.dpm_enabled) return; @@ -1724,6 +1725,7 @@ static void radeon_pm_compute_clocks_dpm(struct radeon_device *rdev) /* update active crtc counts */ rdev->pm.dpm.new_active_crtcs = 0; rdev->pm.dpm.new_active_crtc_count = 0; + rdev->pm.dpm.high_pixelclock_count = 0; if (rdev->num_crtc && rdev->mode_info.mode_config_initialized) { list_for_each_entry(crtc, &ddev->mode_config.crtc_list, head) { @@ -1731,6 +1733,12 @@ static void radeon_pm_compute_clocks_dpm(struct radeon_device *rdev) if (crtc->enabled) { rdev->pm.dpm.new_active_crtcs |= (1 << radeon_crtc->crtc_id); rdev->pm.dpm.new_active_crtc_count++; + if (!radeon_crtc->connector) + continue; + + radeon_connector = to_radeon_connector(radeon_crtc->connector); + if (radeon_connector->pixelclock_for_modeset > 297000) + rdev->pm.dpm.high_pixelclock_count++; } } } diff --git a/drivers/gpu/drm/radeon/si_dpm.c b/drivers/gpu/drm/radeon/si_dpm.c index db2d8b84e137b..aac18d527c01b 100644 --- a/drivers/gpu/drm/radeon/si_dpm.c +++ b/drivers/gpu/drm/radeon/si_dpm.c @@ -3000,6 +3000,9 @@ static void si_apply_state_adjust_rules(struct radeon_device *rdev, (rdev->pdev->device == 0x6605)) { max_sclk = 75000; } + + if (rdev->pm.dpm.high_pixelclock_count > 1) + disable_sclk_switching = true; } if (rps->vce_active) { diff --git a/drivers/hid/hid-ids.h b/drivers/hid/hid-ids.h index 68908dac5835e..75342f3dfb863 100644 --- a/drivers/hid/hid-ids.h +++ b/drivers/hid/hid-ids.h @@ -904,6 +904,7 @@ #define USB_DEVICE_ID_ORTEK_IHOME_IMAC_A210S 0x8003 #define USB_VENDOR_ID_PLANTRONICS 0x047f +#define USB_DEVICE_ID_PLANTRONICS_BLACKWIRE_3220_SERIES 0xc056 #define USB_VENDOR_ID_PANASONIC 0x04da #define USB_DEVICE_ID_PANABOARD_UBT780 0x1044 diff --git a/drivers/hid/hid-plantronics.c b/drivers/hid/hid-plantronics.c index 584b10d3fc3d8..460711c1124ac 100644 --- a/drivers/hid/hid-plantronics.c +++ b/drivers/hid/hid-plantronics.c @@ -16,6 +16,7 @@ #include #include +#include #define PLT_HID_1_0_PAGE 0xffa00000 #define PLT_HID_2_0_PAGE 0xffa20000 @@ -39,6 +40,16 @@ #define PLT_ALLOW_CONSUMER (field->application == HID_CP_CONSUMERCONTROL && \ (usage->hid & HID_USAGE_PAGE) == HID_UP_CONSUMER) +#define PLT_QUIRK_DOUBLE_VOLUME_KEYS BIT(0) + +#define PLT_DOUBLE_KEY_TIMEOUT 5 /* ms */ + +struct plt_drv_data { + unsigned long device_type; + unsigned long last_volume_key_ts; + u32 quirks; +}; + static int plantronics_input_mapping(struct hid_device *hdev, struct hid_input *hi, struct hid_field *field, @@ -46,7 +57,8 @@ static int plantronics_input_mapping(struct hid_device *hdev, unsigned long **bit, int *max) { unsigned short mapped_key; - unsigned long plt_type = (unsigned long)hid_get_drvdata(hdev); + struct plt_drv_data *drv_data = hid_get_drvdata(hdev); + unsigned long plt_type = drv_data->device_type; /* special case for PTT products */ if (field->application == HID_GD_JOYSTICK) @@ -108,6 +120,30 @@ mapped: return 1; } +static int plantronics_event(struct hid_device *hdev, struct hid_field *field, + struct hid_usage *usage, __s32 value) +{ + struct plt_drv_data *drv_data = hid_get_drvdata(hdev); + + if (drv_data->quirks & PLT_QUIRK_DOUBLE_VOLUME_KEYS) { + unsigned long prev_ts, cur_ts; + + /* Usages are filtered in plantronics_usages. */ + + if (!value) /* Handle key presses only. */ + return 0; + + prev_ts = drv_data->last_volume_key_ts; + cur_ts = jiffies; + if (jiffies_to_msecs(cur_ts - prev_ts) <= PLT_DOUBLE_KEY_TIMEOUT) + return 1; /* Ignore the repeated key. */ + + drv_data->last_volume_key_ts = cur_ts; + } + + return 0; +} + static unsigned long plantronics_device_type(struct hid_device *hdev) { unsigned i, col_page; @@ -136,15 +172,24 @@ exit: static int plantronics_probe(struct hid_device *hdev, const struct hid_device_id *id) { + struct plt_drv_data *drv_data; int ret; + drv_data = devm_kzalloc(&hdev->dev, sizeof(*drv_data), GFP_KERNEL); + if (!drv_data) + return -ENOMEM; + ret = hid_parse(hdev); if (ret) { hid_err(hdev, "parse failed\n"); goto err; } - hid_set_drvdata(hdev, (void *)plantronics_device_type(hdev)); + drv_data->device_type = plantronics_device_type(hdev); + drv_data->quirks = id->driver_data; + drv_data->last_volume_key_ts = jiffies - msecs_to_jiffies(PLT_DOUBLE_KEY_TIMEOUT); + + hid_set_drvdata(hdev, drv_data); ret = hid_hw_start(hdev, HID_CONNECT_DEFAULT | HID_CONNECT_HIDINPUT_FORCE | HID_CONNECT_HIDDEV_FORCE); @@ -156,15 +201,26 @@ err: } static const struct hid_device_id plantronics_devices[] = { + { HID_USB_DEVICE(USB_VENDOR_ID_PLANTRONICS, + USB_DEVICE_ID_PLANTRONICS_BLACKWIRE_3220_SERIES), + .driver_data = PLT_QUIRK_DOUBLE_VOLUME_KEYS }, { HID_USB_DEVICE(USB_VENDOR_ID_PLANTRONICS, HID_ANY_ID) }, { } }; MODULE_DEVICE_TABLE(hid, plantronics_devices); +static const struct hid_usage_id plantronics_usages[] = { + { HID_CP_VOLUMEUP, EV_KEY, HID_ANY_ID }, + { HID_CP_VOLUMEDOWN, EV_KEY, HID_ANY_ID }, + { HID_TERMINATOR, HID_TERMINATOR, HID_TERMINATOR } +}; + static struct hid_driver plantronics_driver = { .name = "plantronics", .id_table = plantronics_devices, + .usage_table = plantronics_usages, .input_mapping = plantronics_input_mapping, + .event = plantronics_event, .probe = plantronics_probe, }; module_hid_driver(plantronics_driver); diff --git a/drivers/hsi/hsi_core.c b/drivers/hsi/hsi_core.c index 9065efd21851d..71895da63810b 100644 --- a/drivers/hsi/hsi_core.c +++ b/drivers/hsi/hsi_core.c @@ -223,8 +223,6 @@ static void hsi_add_client_from_dt(struct hsi_port *port, if (err) goto err; - dev_set_name(&cl->device, "%s", name); - err = hsi_of_property_parse_mode(client, "hsi-mode", &mode); if (err) { err = hsi_of_property_parse_mode(client, "hsi-rx-mode", @@ -306,6 +304,7 @@ static void hsi_add_client_from_dt(struct hsi_port *port, cl->device.release = hsi_client_release; cl->device.of_node = client; + dev_set_name(&cl->device, "%s", name); if (device_register(&cl->device) < 0) { pr_err("hsi: failed to register client: %s\n", name); put_device(&cl->device); diff --git a/drivers/hv/channel_mgmt.c b/drivers/hv/channel_mgmt.c index ac9617671757c..cdd4392c589d3 100644 --- a/drivers/hv/channel_mgmt.c +++ b/drivers/hv/channel_mgmt.c @@ -773,6 +773,12 @@ static void init_vp_index(struct vmbus_channel *channel, u16 dev_type) free_cpumask_var(available_mask); } +#define UNLOAD_DELAY_UNIT_MS 10 /* 10 milliseconds */ +#define UNLOAD_WAIT_MS (100*1000) /* 100 seconds */ +#define UNLOAD_WAIT_LOOPS (UNLOAD_WAIT_MS/UNLOAD_DELAY_UNIT_MS) +#define UNLOAD_MSG_MS (5*1000) /* Every 5 seconds */ +#define UNLOAD_MSG_LOOPS (UNLOAD_MSG_MS/UNLOAD_DELAY_UNIT_MS) + static void vmbus_wait_for_unload(void) { int cpu; @@ -790,12 +796,17 @@ static void vmbus_wait_for_unload(void) * vmbus_connection.unload_event. If not, the last thing we can do is * read message pages for all CPUs directly. * - * Wait no more than 10 seconds so that the panic path can't get - * hung forever in case the response message isn't seen. + * Wait up to 100 seconds since an Azure host must writeback any dirty + * data in its disk cache before the VMbus UNLOAD request will + * complete. This flushing has been empirically observed to take up + * to 50 seconds in cases with a lot of dirty data, so allow additional + * leeway and for inaccuracies in mdelay(). But eventually time out so + * that the panic path can't get hung forever in case the response + * message isn't seen. */ - for (i = 0; i < 1000; i++) { + for (i = 1; i <= UNLOAD_WAIT_LOOPS; i++) { if (completion_done(&vmbus_connection.unload_event)) - break; + goto completed; for_each_online_cpu(cpu) { struct hv_per_cpu_context *hv_cpu @@ -818,9 +829,18 @@ static void vmbus_wait_for_unload(void) vmbus_signal_eom(msg, message_type); } - mdelay(10); + /* + * Give a notice periodically so someone watching the + * serial output won't think it is completely hung. + */ + if (!(i % UNLOAD_MSG_LOOPS)) + pr_notice("Waiting for VMBus UNLOAD to complete\n"); + + mdelay(UNLOAD_DELAY_UNIT_MS); } + pr_err("Continuing even though VMBus UNLOAD did not complete\n"); +completed: /* * We're crashing and already got the UNLOAD_RESPONSE, cleanup all * maybe-pending messages on all CPUs to be able to receive new diff --git a/drivers/hwtracing/intel_th/gth.c b/drivers/hwtracing/intel_th/gth.c index edc52d75e6bdc..5041fe7fee9ed 100644 --- a/drivers/hwtracing/intel_th/gth.c +++ b/drivers/hwtracing/intel_th/gth.c @@ -477,7 +477,7 @@ static void intel_th_gth_disable(struct intel_th_device *thdev, output->active = false; for_each_set_bit(master, gth->output[output->port].master, - TH_CONFIGURABLE_MASTERS) { + TH_CONFIGURABLE_MASTERS + 1) { gth_master_set(gth, master, -1); } spin_unlock(>h->gth_lock); @@ -616,7 +616,7 @@ static void intel_th_gth_unassign(struct intel_th_device *thdev, othdev->output.port = -1; othdev->output.active = false; gth->output[port].output = NULL; - for (master = 0; master <= TH_CONFIGURABLE_MASTERS; master++) + for (master = 0; master < TH_CONFIGURABLE_MASTERS + 1; master++) if (gth->master[master] == port) gth->master[master] = -1; spin_unlock(>h->gth_lock); diff --git a/drivers/hwtracing/intel_th/pci.c b/drivers/hwtracing/intel_th/pci.c index 2a16171033941..83fab06ccfebd 100644 --- a/drivers/hwtracing/intel_th/pci.c +++ b/drivers/hwtracing/intel_th/pci.c @@ -240,6 +240,16 @@ static const struct pci_device_id intel_th_pci_id_table[] = { PCI_DEVICE(PCI_VENDOR_ID_INTEL, 0x1bcc), .driver_data = (kernel_ulong_t)&intel_th_2x, }, + { + /* Alder Lake-M */ + PCI_DEVICE(PCI_VENDOR_ID_INTEL, 0x54a6), + .driver_data = (kernel_ulong_t)&intel_th_2x, + }, + { + /* Rocket Lake CPU */ + PCI_DEVICE(PCI_VENDOR_ID_INTEL, 0x4c19), + .driver_data = (kernel_ulong_t)&intel_th_2x, + }, { 0 }, }; diff --git a/drivers/i2c/busses/i2c-cadence.c b/drivers/i2c/busses/i2c-cadence.c index b136057182916..c5475bb4fae6b 100644 --- a/drivers/i2c/busses/i2c-cadence.c +++ b/drivers/i2c/busses/i2c-cadence.c @@ -906,7 +906,10 @@ static int cdns_i2c_probe(struct platform_device *pdev) if (IS_ERR(id->membase)) return PTR_ERR(id->membase); - id->irq = platform_get_irq(pdev, 0); + ret = platform_get_irq(pdev, 0); + if (ret < 0) + return ret; + id->irq = ret; id->adap.owner = THIS_MODULE; id->adap.dev.of_node = pdev->dev.of_node; diff --git a/drivers/i2c/busses/i2c-emev2.c b/drivers/i2c/busses/i2c-emev2.c index 959d4912ec0d5..0230a13a6ab72 100644 --- a/drivers/i2c/busses/i2c-emev2.c +++ b/drivers/i2c/busses/i2c-emev2.c @@ -397,7 +397,10 @@ static int em_i2c_probe(struct platform_device *pdev) em_i2c_reset(&priv->adap); - priv->irq = platform_get_irq(pdev, 0); + ret = platform_get_irq(pdev, 0); + if (ret < 0) + goto err_clk; + priv->irq = ret; ret = devm_request_irq(&pdev->dev, priv->irq, em_i2c_irq_handler, 0, "em_i2c", priv); if (ret) diff --git a/drivers/i2c/busses/i2c-jz4780.c b/drivers/i2c/busses/i2c-jz4780.c index 41ca9ff7b5da7..4dd800c0db14a 100644 --- a/drivers/i2c/busses/i2c-jz4780.c +++ b/drivers/i2c/busses/i2c-jz4780.c @@ -760,7 +760,10 @@ static int jz4780_i2c_probe(struct platform_device *pdev) jz4780_i2c_writew(i2c, JZ4780_I2C_INTM, 0x0); - i2c->irq = platform_get_irq(pdev, 0); + ret = platform_get_irq(pdev, 0); + if (ret < 0) + goto err; + i2c->irq = ret; ret = devm_request_irq(&pdev->dev, i2c->irq, jz4780_i2c_irq, 0, dev_name(&pdev->dev), i2c); if (ret) diff --git a/drivers/i2c/busses/i2c-sh7760.c b/drivers/i2c/busses/i2c-sh7760.c index c2005c789d2b0..319d1fa617c88 100644 --- a/drivers/i2c/busses/i2c-sh7760.c +++ b/drivers/i2c/busses/i2c-sh7760.c @@ -471,7 +471,10 @@ static int sh7760_i2c_probe(struct platform_device *pdev) goto out2; } - id->irq = platform_get_irq(pdev, 0); + ret = platform_get_irq(pdev, 0); + if (ret < 0) + goto out3; + id->irq = ret; id->adap.nr = pdev->id; id->adap.algo = &sh7760_i2c_algo; diff --git a/drivers/i2c/i2c-dev.c b/drivers/i2c/i2c-dev.c index cbda91a0cb5f8..1d10ee86299d8 100644 --- a/drivers/i2c/i2c-dev.c +++ b/drivers/i2c/i2c-dev.c @@ -448,8 +448,13 @@ static long i2cdev_ioctl(struct file *file, unsigned int cmd, unsigned long arg) sizeof(rdwr_arg))) return -EFAULT; - /* Put an arbitrary limit on the number of messages that can - * be sent at once */ + if (!rdwr_arg.msgs || rdwr_arg.nmsgs == 0) + return -EINVAL; + + /* + * Put an arbitrary limit on the number of messages that can + * be sent at once + */ if (rdwr_arg.nmsgs > I2C_RDWR_IOCTL_MAX_MSGS) return -EINVAL; diff --git a/drivers/iio/accel/adis16201.c b/drivers/iio/accel/adis16201.c index 4c1d482ea73a7..94a80f8fdd10b 100644 --- a/drivers/iio/accel/adis16201.c +++ b/drivers/iio/accel/adis16201.c @@ -216,7 +216,7 @@ static const struct iio_chan_spec adis16201_channels[] = { ADIS_AUX_ADC_CHAN(ADIS16201_AUX_ADC_REG, ADIS16201_SCAN_AUX_ADC, 0, 12), ADIS_INCLI_CHAN(X, ADIS16201_XINCL_OUT_REG, ADIS16201_SCAN_INCLI_X, BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14), - ADIS_INCLI_CHAN(X, ADIS16201_YINCL_OUT_REG, ADIS16201_SCAN_INCLI_Y, + ADIS_INCLI_CHAN(Y, ADIS16201_YINCL_OUT_REG, ADIS16201_SCAN_INCLI_Y, BIT(IIO_CHAN_INFO_CALIBBIAS), 0, 14), IIO_CHAN_SOFT_TIMESTAMP(7) }; diff --git a/drivers/iio/gyro/mpu3050-core.c b/drivers/iio/gyro/mpu3050-core.c index 33120ccff87ff..e6fdd0f4b4bcb 100644 --- a/drivers/iio/gyro/mpu3050-core.c +++ b/drivers/iio/gyro/mpu3050-core.c @@ -270,7 +270,16 @@ static int mpu3050_read_raw(struct iio_dev *indio_dev, case IIO_CHAN_INFO_OFFSET: switch (chan->type) { case IIO_TEMP: - /* The temperature scaling is (x+23000)/280 Celsius */ + /* + * The temperature scaling is (x+23000)/280 Celsius + * for the "best fit straight line" temperature range + * of -30C..85C. The 23000 includes room temperature + * offset of +35C, 280 is the precision scale and x is + * the 16-bit signed integer reported by hardware. + * + * Temperature value itself represents temperature of + * the sensor die. + */ *val = 23000; return IIO_VAL_INT; default: @@ -327,7 +336,7 @@ static int mpu3050_read_raw(struct iio_dev *indio_dev, goto out_read_raw_unlock; } - *val = be16_to_cpu(raw_val); + *val = (s16)be16_to_cpu(raw_val); ret = IIO_VAL_INT; goto out_read_raw_unlock; diff --git a/drivers/iio/light/tsl2583.c b/drivers/iio/light/tsl2583.c index 4b5d9988f0256..23295fec5be59 100644 --- a/drivers/iio/light/tsl2583.c +++ b/drivers/iio/light/tsl2583.c @@ -350,6 +350,14 @@ static int tsl2583_als_calibrate(struct iio_dev *indio_dev) return lux_val; } + /* Avoid division by zero of lux_value later on */ + if (lux_val == 0) { + dev_err(&chip->client->dev, + "%s: lux_val of 0 will produce out of range trim_value\n", + __func__); + return -ENODATA; + } + gain_trim_val = (unsigned int)(((chip->als_settings.als_cal_target) * chip->als_settings.als_gain_trim) / lux_val); if ((gain_trim_val < 250) || (gain_trim_val > 4000)) { diff --git a/drivers/iio/proximity/pulsedlight-lidar-lite-v2.c b/drivers/iio/proximity/pulsedlight-lidar-lite-v2.c index 47af54f14756b..67f85268b63db 100644 --- a/drivers/iio/proximity/pulsedlight-lidar-lite-v2.c +++ b/drivers/iio/proximity/pulsedlight-lidar-lite-v2.c @@ -158,6 +158,7 @@ static int lidar_get_measurement(struct lidar_data *data, u16 *reg) ret = lidar_write_control(data, LIDAR_REG_CONTROL_ACQUIRE); if (ret < 0) { dev_err(&client->dev, "cannot send start measurement command"); + pm_runtime_put_noidle(&client->dev); return ret; } diff --git a/drivers/infiniband/hw/bnxt_re/qplib_res.c b/drivers/infiniband/hw/bnxt_re/qplib_res.c index 539a5d44e6dbe..655952a6c0e60 100644 --- a/drivers/infiniband/hw/bnxt_re/qplib_res.c +++ b/drivers/infiniband/hw/bnxt_re/qplib_res.c @@ -725,6 +725,7 @@ static int bnxt_qplib_alloc_dpi_tbl(struct bnxt_qplib_res *res, unmap_io: pci_iounmap(res->pdev, dpit->dbr_bar_reg_iomem); + dpit->dbr_bar_reg_iomem = NULL; return -ENOMEM; } diff --git a/drivers/infiniband/hw/hfi1/firmware.c b/drivers/infiniband/hw/hfi1/firmware.c index 2b57ba70ddd6a..c090807124858 100644 --- a/drivers/infiniband/hw/hfi1/firmware.c +++ b/drivers/infiniband/hw/hfi1/firmware.c @@ -1924,6 +1924,7 @@ int parse_platform_config(struct hfi1_devdata *dd) dd_dev_err(dd, "%s: Failed CRC check at offset %ld\n", __func__, (ptr - (u32 *)dd->platform_config.data)); + ret = -EINVAL; goto bail; } /* Jump the CRC DWORD */ diff --git a/drivers/infiniband/hw/i40iw/i40iw_pble.c b/drivers/infiniband/hw/i40iw/i40iw_pble.c index 540aab5e502dd..3fafc5424e76d 100644 --- a/drivers/infiniband/hw/i40iw/i40iw_pble.c +++ b/drivers/infiniband/hw/i40iw/i40iw_pble.c @@ -392,12 +392,9 @@ static enum i40iw_status_code add_pble_pool(struct i40iw_sc_dev *dev, i40iw_debug(dev, I40IW_DEBUG_PBLE, "next_fpm_addr = %llx chunk_size[%u] = 0x%x\n", pble_rsrc->next_fpm_addr, chunk->size, chunk->size); pble_rsrc->unallocated_pble -= (chunk->size >> 3); - list_add(&chunk->list, &pble_rsrc->pinfo.clist); sd_reg_val = (sd_entry_type == I40IW_SD_TYPE_PAGED) ? sd_entry->u.pd_table.pd_page_addr.pa : sd_entry->u.bp.addr.pa; - if (sd_entry->valid) - return 0; - if (dev->is_pf) { + if (dev->is_pf && !sd_entry->valid) { ret_code = i40iw_hmc_sd_one(dev, hmc_info->hmc_fn_id, sd_reg_val, idx->sd_idx, sd_entry->entry_type, true); @@ -408,6 +405,7 @@ static enum i40iw_status_code add_pble_pool(struct i40iw_sc_dev *dev, } sd_entry->valid = true; + list_add(&chunk->list, &pble_rsrc->pinfo.clist); return 0; error: kfree(chunk); diff --git a/drivers/infiniband/ulp/srpt/ib_srpt.c b/drivers/infiniband/ulp/srpt/ib_srpt.c index bc979a85a505d..6090f1ce0c56f 100644 --- a/drivers/infiniband/ulp/srpt/ib_srpt.c +++ b/drivers/infiniband/ulp/srpt/ib_srpt.c @@ -2301,6 +2301,7 @@ static int srpt_cm_req_recv(struct srpt_device *const sdev, pr_info("rejected SRP_LOGIN_REQ because target %s_%d is not enabled\n", sdev->device->name, port_num); mutex_unlock(&sport->mutex); + ret = -EINVAL; goto reject; } diff --git a/drivers/input/touchscreen/elants_i2c.c b/drivers/input/touchscreen/elants_i2c.c index d21ca39b0fdb0..adfae2d88707b 100644 --- a/drivers/input/touchscreen/elants_i2c.c +++ b/drivers/input/touchscreen/elants_i2c.c @@ -41,6 +41,7 @@ #include #include #include +#include #include /* Device, Driver information */ @@ -1131,6 +1132,40 @@ static void elants_i2c_power_off(void *_data) } } +#ifdef CONFIG_ACPI +static const struct acpi_device_id i2c_hid_ids[] = { + {"ACPI0C50", 0 }, + {"PNP0C50", 0 }, + { }, +}; + +static const guid_t i2c_hid_guid = + GUID_INIT(0x3CDFF6F7, 0x4267, 0x4555, + 0xAD, 0x05, 0xB3, 0x0A, 0x3D, 0x89, 0x38, 0xDE); + +static bool elants_acpi_is_hid_device(struct device *dev) +{ + acpi_handle handle = ACPI_HANDLE(dev); + union acpi_object *obj; + + if (acpi_match_device_ids(ACPI_COMPANION(dev), i2c_hid_ids)) + return false; + + obj = acpi_evaluate_dsm_typed(handle, &i2c_hid_guid, 1, 1, NULL, ACPI_TYPE_INTEGER); + if (obj) { + ACPI_FREE(obj); + return true; + } + + return false; +} +#else +static bool elants_acpi_is_hid_device(struct device *dev) +{ + return false; +} +#endif + static int elants_i2c_probe(struct i2c_client *client, const struct i2c_device_id *id) { @@ -1139,9 +1174,14 @@ static int elants_i2c_probe(struct i2c_client *client, unsigned long irqflags; int error; + /* Don't bind to i2c-hid compatible devices, these are handled by the i2c-hid drv. */ + if (elants_acpi_is_hid_device(&client->dev)) { + dev_warn(&client->dev, "This device appears to be an I2C-HID device, not binding\n"); + return -ENODEV; + } + if (!i2c_check_functionality(client->adapter, I2C_FUNC_I2C)) { - dev_err(&client->dev, - "%s: i2c check functionality error\n", DEVICE_NAME); + dev_err(&client->dev, "I2C check functionality error\n"); return -ENXIO; } diff --git a/drivers/input/touchscreen/silead.c b/drivers/input/touchscreen/silead.c index 06f0eb04a8fd4..a787a6aefc69f 100644 --- a/drivers/input/touchscreen/silead.c +++ b/drivers/input/touchscreen/silead.c @@ -28,6 +28,7 @@ #include #include #include +#include #include #include @@ -343,10 +344,8 @@ static int silead_ts_get_id(struct i2c_client *client) error = i2c_smbus_read_i2c_block_data(client, SILEAD_REG_ID, sizeof(chip_id), (u8 *)&chip_id); - if (error < 0) { - dev_err(&client->dev, "Chip ID read error %d\n", error); + if (error < 0) return error; - } data->chip_id = le32_to_cpu(chip_id); dev_info(&client->dev, "Silead chip ID: 0x%8X", data->chip_id); @@ -359,12 +358,49 @@ static int silead_ts_setup(struct i2c_client *client) int error; u32 status; + /* + * Some buggy BIOS-es bring up the chip in a stuck state where it + * blocks the I2C bus. The following steps are necessary to + * unstuck the chip / bus: + * 1. Turn off the Silead chip. + * 2. Try to do an I2C transfer with the chip, this will fail in + * response to which the I2C-bus-driver will call: + * i2c_recover_bus() which will unstuck the I2C-bus. Note the + * unstuck-ing of the I2C bus only works if we first drop the + * chip off the bus by turning it off. + * 3. Turn the chip back on. + * + * On the x86/ACPI systems were this problem is seen, step 1. and + * 3. require making ACPI calls and dealing with ACPI Power + * Resources. The workaround below runtime-suspends the chip to + * turn it off, leaving it up to the ACPI subsystem to deal with + * this. + */ + + if (device_property_read_bool(&client->dev, + "silead,stuck-controller-bug")) { + pm_runtime_set_active(&client->dev); + pm_runtime_enable(&client->dev); + pm_runtime_allow(&client->dev); + + pm_runtime_suspend(&client->dev); + + dev_warn(&client->dev, FW_BUG "Stuck I2C bus: please ignore the next 'controller timed out' error\n"); + silead_ts_get_id(client); + + /* The forbid will also resume the device */ + pm_runtime_forbid(&client->dev); + pm_runtime_disable(&client->dev); + } + silead_ts_set_power(client, SILEAD_POWER_OFF); silead_ts_set_power(client, SILEAD_POWER_ON); error = silead_ts_get_id(client); - if (error) + if (error) { + dev_err(&client->dev, "Chip ID read error %d\n", error); return error; + } error = silead_ts_init(client); if (error) diff --git a/drivers/irqchip/irq-gic-v3-mbi.c b/drivers/irqchip/irq-gic-v3-mbi.c index fbfa7ff6deb16..9d011281d4b5c 100644 --- a/drivers/irqchip/irq-gic-v3-mbi.c +++ b/drivers/irqchip/irq-gic-v3-mbi.c @@ -297,7 +297,7 @@ int __init mbi_init(struct fwnode_handle *fwnode, struct irq_domain *parent) reg = of_get_property(np, "mbi-alias", NULL); if (reg) { mbi_phys_base = of_translate_address(np, reg); - if (mbi_phys_base == OF_BAD_ADDR) { + if (mbi_phys_base == (phys_addr_t)OF_BAD_ADDR) { ret = -ENXIO; goto err_free_mbi; } diff --git a/drivers/isdn/capi/kcapi.c b/drivers/isdn/capi/kcapi.c index a4ceb61c5b603..18de41a266ebe 100644 --- a/drivers/isdn/capi/kcapi.c +++ b/drivers/isdn/capi/kcapi.c @@ -846,7 +846,7 @@ EXPORT_SYMBOL(capi20_put_message); * Return value: CAPI result code */ -u16 capi20_get_manufacturer(u32 contr, u8 *buf) +u16 capi20_get_manufacturer(u32 contr, u8 buf[CAPI_MANUFACTURER_LEN]) { struct capi_ctr *ctr; u16 ret; @@ -916,7 +916,7 @@ EXPORT_SYMBOL(capi20_get_version); * Return value: CAPI result code */ -u16 capi20_get_serial(u32 contr, u8 *serial) +u16 capi20_get_serial(u32 contr, u8 serial[CAPI_SERIAL_LEN]) { struct capi_ctr *ctr; u16 ret; diff --git a/drivers/md/dm-raid.c b/drivers/md/dm-raid.c index 23de59a692c51..b163329172208 100644 --- a/drivers/md/dm-raid.c +++ b/drivers/md/dm-raid.c @@ -1892,6 +1892,14 @@ static bool rs_takeover_requested(struct raid_set *rs) return rs->md.new_level != rs->md.level; } +/* True if layout is set to reshape. */ +static bool rs_is_layout_change(struct raid_set *rs, bool use_mddev) +{ + return (use_mddev ? rs->md.delta_disks : rs->delta_disks) || + rs->md.new_layout != rs->md.layout || + rs->md.new_chunk_sectors != rs->md.chunk_sectors; +} + /* True if @rs is requested to reshape by ctr */ static bool rs_reshape_requested(struct raid_set *rs) { @@ -1904,9 +1912,7 @@ static bool rs_reshape_requested(struct raid_set *rs) if (rs_is_raid0(rs)) return false; - change = mddev->new_layout != mddev->layout || - mddev->new_chunk_sectors != mddev->chunk_sectors || - rs->delta_disks; + change = rs_is_layout_change(rs, false); /* Historical case to support raid1 reshape without delta disks */ if (rs_is_raid1(rs)) { @@ -2843,7 +2849,7 @@ static sector_t _get_reshape_sectors(struct raid_set *rs) } /* - * + * Reshape: * - change raid layout * - change chunk size * - add disks @@ -2952,6 +2958,20 @@ static int rs_setup_reshape(struct raid_set *rs) return r; } +/* + * If the md resync thread has updated superblock with max reshape position + * at the end of a reshape but not (yet) reset the layout configuration + * changes -> reset the latter. + */ +static void rs_reset_inconclusive_reshape(struct raid_set *rs) +{ + if (!rs_is_reshaping(rs) && rs_is_layout_change(rs, true)) { + rs_set_cur(rs); + rs->md.delta_disks = 0; + rs->md.reshape_backwards = 0; + } +} + /* * Enable/disable discard support on RAID set depending on * RAID level and discard properties of underlying RAID members. @@ -3221,11 +3241,14 @@ static int raid_ctr(struct dm_target *ti, unsigned int argc, char **argv) if (r) goto bad; + /* Catch any inconclusive reshape superblock content. */ + rs_reset_inconclusive_reshape(rs); + /* Start raid set read-only and assumed clean to change in raid_resume() */ rs->md.ro = 1; rs->md.in_sync = 1; - /* Keep array frozen */ + /* Keep array frozen until resume. */ set_bit(MD_RECOVERY_FROZEN, &rs->md.recovery); /* Has to be held on running the array */ @@ -3239,7 +3262,6 @@ static int raid_ctr(struct dm_target *ti, unsigned int argc, char **argv) } r = md_start(&rs->md); - if (r) { ti->error = "Failed to start raid array"; mddev_unlock(&rs->md); diff --git a/drivers/md/dm-rq.c b/drivers/md/dm-rq.c index 9fde174ce3961..2957a3763f019 100644 --- a/drivers/md/dm-rq.c +++ b/drivers/md/dm-rq.c @@ -831,6 +831,7 @@ out_tag_set: blk_mq_free_tag_set(md->tag_set); out_kfree_tag_set: kfree(md->tag_set); + md->tag_set = NULL; return err; } @@ -840,6 +841,7 @@ void dm_mq_cleanup_mapped_device(struct mapped_device *md) if (md->tag_set) { blk_mq_free_tag_set(md->tag_set); kfree(md->tag_set); + md->tag_set = NULL; } } diff --git a/drivers/md/md-bitmap.c b/drivers/md/md-bitmap.c index 503f5e06fa86f..e79d2aa2372f4 100644 --- a/drivers/md/md-bitmap.c +++ b/drivers/md/md-bitmap.c @@ -1725,6 +1725,8 @@ void md_bitmap_flush(struct mddev *mddev) md_bitmap_daemon_work(mddev); bitmap->daemon_lastrun -= sleep; md_bitmap_daemon_work(mddev); + if (mddev->bitmap_info.external) + md_super_wait(mddev); md_bitmap_update_sb(bitmap); } diff --git a/drivers/md/md.c b/drivers/md/md.c index 09f0d8e70b709..fae6a983ceee1 100644 --- a/drivers/md/md.c +++ b/drivers/md/md.c @@ -583,7 +583,34 @@ void mddev_init(struct mddev *mddev) } EXPORT_SYMBOL_GPL(mddev_init); +static struct mddev *mddev_find_locked(dev_t unit) +{ + struct mddev *mddev; + + list_for_each_entry(mddev, &all_mddevs, all_mddevs) + if (mddev->unit == unit) + return mddev; + + return NULL; +} + static struct mddev *mddev_find(dev_t unit) +{ + struct mddev *mddev; + + if (MAJOR(unit) != MD_MAJOR) + unit &= ~((1 << MdpMinorShift) - 1); + + spin_lock(&all_mddevs_lock); + mddev = mddev_find_locked(unit); + if (mddev) + mddev_get(mddev); + spin_unlock(&all_mddevs_lock); + + return mddev; +} + +static struct mddev *mddev_find_or_alloc(dev_t unit) { struct mddev *mddev, *new = NULL; @@ -594,13 +621,13 @@ static struct mddev *mddev_find(dev_t unit) spin_lock(&all_mddevs_lock); if (unit) { - list_for_each_entry(mddev, &all_mddevs, all_mddevs) - if (mddev->unit == unit) { - mddev_get(mddev); - spin_unlock(&all_mddevs_lock); - kfree(new); - return mddev; - } + mddev = mddev_find_locked(unit); + if (mddev) { + mddev_get(mddev); + spin_unlock(&all_mddevs_lock); + kfree(new); + return mddev; + } if (new) { list_add(&new->all_mddevs, &all_mddevs); @@ -626,12 +653,7 @@ static struct mddev *mddev_find(dev_t unit) return NULL; } - is_free = 1; - list_for_each_entry(mddev, &all_mddevs, all_mddevs) - if (mddev->unit == dev) { - is_free = 0; - break; - } + is_free = !mddev_find_locked(dev); } new->unit = dev; new->md_minor = MINOR(dev); @@ -5302,7 +5324,7 @@ static int md_alloc(dev_t dev, char *name) * writing to /sys/module/md_mod/parameters/new_array. */ static DEFINE_MUTEX(disks_mutex); - struct mddev *mddev = mddev_find(dev); + struct mddev *mddev = mddev_find_or_alloc(dev); struct gendisk *disk; int partitioned; int shift; @@ -6155,11 +6177,9 @@ static void autorun_devices(int part) md_probe(dev, NULL, NULL); mddev = mddev_find(dev); - if (!mddev || !mddev->gendisk) { - if (mddev) - mddev_put(mddev); + if (!mddev) break; - } + if (mddev_lock(mddev)) pr_warn("md: %s locked, cannot run\n", mdname(mddev)); else if (mddev->raid_disks || mddev->major_version @@ -7461,8 +7481,7 @@ static int md_open(struct block_device *bdev, fmode_t mode) /* Wait until bdev->bd_disk is definitely gone */ if (work_pending(&mddev->del_work)) flush_workqueue(md_misc_wq); - /* Then retry the open from the top */ - return -ERESTARTSYS; + return -EBUSY; } BUG_ON(mddev != bdev->bd_disk->private_data); @@ -7795,7 +7814,11 @@ static void *md_seq_start(struct seq_file *seq, loff_t *pos) loff_t l = *pos; struct mddev *mddev; - if (l >= 0x10000) + if (l == 0x10000) { + ++*pos; + return (void *)2; + } + if (l > 0x10000) return NULL; if (!l--) /* header */ @@ -8883,11 +8906,11 @@ void md_check_recovery(struct mddev *mddev) } if (mddev_is_clustered(mddev)) { - struct md_rdev *rdev; + struct md_rdev *rdev, *tmp; /* kick the device if another node issued a * remove disk. */ - rdev_for_each(rdev, mddev) { + rdev_for_each_safe(rdev, tmp, mddev) { if (test_and_clear_bit(ClusterRemove, &rdev->flags) && rdev->raid_disk < 0) md_kick_rdev_from_array(rdev); @@ -9187,7 +9210,7 @@ err_wq: static void check_sb_changes(struct mddev *mddev, struct md_rdev *rdev) { struct mdp_superblock_1 *sb = page_address(rdev->sb_page); - struct md_rdev *rdev2; + struct md_rdev *rdev2, *tmp; int role, ret; char b[BDEVNAME_SIZE]; @@ -9204,7 +9227,7 @@ static void check_sb_changes(struct mddev *mddev, struct md_rdev *rdev) } /* Check for change of roles in the active devices */ - rdev_for_each(rdev2, mddev) { + rdev_for_each_safe(rdev2, tmp, mddev) { if (test_bit(Faulty, &rdev2->flags)) continue; diff --git a/drivers/md/persistent-data/dm-btree-internal.h b/drivers/md/persistent-data/dm-btree-internal.h index a240990a7f333..5673f8eb5f88f 100644 --- a/drivers/md/persistent-data/dm-btree-internal.h +++ b/drivers/md/persistent-data/dm-btree-internal.h @@ -34,12 +34,12 @@ struct node_header { __le32 max_entries; __le32 value_size; __le32 padding; -} __packed; +} __attribute__((packed, aligned(8))); struct btree_node { struct node_header header; __le64 keys[0]; -} __packed; +} __attribute__((packed, aligned(8))); /* diff --git a/drivers/md/persistent-data/dm-space-map-common.c b/drivers/md/persistent-data/dm-space-map-common.c index 17aef55ed708a..a284762e548e1 100644 --- a/drivers/md/persistent-data/dm-space-map-common.c +++ b/drivers/md/persistent-data/dm-space-map-common.c @@ -337,6 +337,8 @@ int sm_ll_find_free_block(struct ll_disk *ll, dm_block_t begin, */ begin = do_div(index_begin, ll->entries_per_block); end = do_div(end, ll->entries_per_block); + if (end == 0) + end = ll->entries_per_block; for (i = index_begin; i < index_end; i++, begin = 0) { struct dm_block *blk; diff --git a/drivers/md/persistent-data/dm-space-map-common.h b/drivers/md/persistent-data/dm-space-map-common.h index 8de63ce39bdd5..87e17909ef521 100644 --- a/drivers/md/persistent-data/dm-space-map-common.h +++ b/drivers/md/persistent-data/dm-space-map-common.h @@ -33,7 +33,7 @@ struct disk_index_entry { __le64 blocknr; __le32 nr_free; __le32 none_free_before; -} __packed; +} __attribute__ ((packed, aligned(8))); #define MAX_METADATA_BITMAPS 255 @@ -43,7 +43,7 @@ struct disk_metadata_index { __le64 blocknr; struct disk_index_entry index[MAX_METADATA_BITMAPS]; -} __packed; +} __attribute__ ((packed, aligned(8))); struct ll_disk; @@ -86,7 +86,7 @@ struct disk_sm_root { __le64 nr_allocated; __le64 bitmap_root; __le64 ref_count_root; -} __packed; +} __attribute__ ((packed, aligned(8))); #define ENTRIES_PER_BYTE 4 @@ -94,7 +94,7 @@ struct disk_bitmap_header { __le32 csum; __le32 not_used; __le64 blocknr; -} __packed; +} __attribute__ ((packed, aligned(8))); enum allocation_event { SM_NONE, diff --git a/drivers/md/raid1.c b/drivers/md/raid1.c index abcb4c3a76c18..876d3e1339d17 100644 --- a/drivers/md/raid1.c +++ b/drivers/md/raid1.c @@ -445,6 +445,8 @@ static void raid1_end_write_request(struct bio *bio) if (!test_bit(Faulty, &rdev->flags)) set_bit(R1BIO_WriteError, &r1_bio->state); else { + /* Fail the request */ + set_bit(R1BIO_Degraded, &r1_bio->state); /* Finished with this branch */ r1_bio->bios[mirror] = NULL; to_put = bio; diff --git a/drivers/media/dvb-core/dvbdev.c b/drivers/media/dvb-core/dvbdev.c index 04dc2f4bc7aaf..d8f19a4d214aa 100644 --- a/drivers/media/dvb-core/dvbdev.c +++ b/drivers/media/dvb-core/dvbdev.c @@ -241,6 +241,7 @@ static void dvb_media_device_free(struct dvb_device *dvbdev) if (dvbdev->adapter->conn) { media_device_unregister_entity(dvbdev->adapter->conn); + kfree(dvbdev->adapter->conn); dvbdev->adapter->conn = NULL; kfree(dvbdev->adapter->conn_pads); dvbdev->adapter->conn_pads = NULL; diff --git a/drivers/media/i2c/adv7511-v4l2.c b/drivers/media/i2c/adv7511-v4l2.c index 6869bb593a682..4052abeead502 100644 --- a/drivers/media/i2c/adv7511-v4l2.c +++ b/drivers/media/i2c/adv7511-v4l2.c @@ -1965,7 +1965,7 @@ static int adv7511_remove(struct i2c_client *client) adv7511_set_isr(sd, false); adv7511_init_setup(sd); - cancel_delayed_work(&state->edid_handler); + cancel_delayed_work_sync(&state->edid_handler); i2c_unregister_device(state->i2c_edid); if (state->i2c_cec) i2c_unregister_device(state->i2c_cec); diff --git a/drivers/media/i2c/adv7604.c b/drivers/media/i2c/adv7604.c index a4b0a89c7e7e6..04577d409e63c 100644 --- a/drivers/media/i2c/adv7604.c +++ b/drivers/media/i2c/adv7604.c @@ -3560,7 +3560,7 @@ static int adv76xx_remove(struct i2c_client *client) io_write(sd, 0x6e, 0); io_write(sd, 0x73, 0); - cancel_delayed_work(&state->delayed_work_enable_hotplug); + cancel_delayed_work_sync(&state->delayed_work_enable_hotplug); v4l2_async_unregister_subdev(sd); media_entity_cleanup(&sd->entity); adv76xx_unregister_clients(to_state(sd)); diff --git a/drivers/media/i2c/adv7842.c b/drivers/media/i2c/adv7842.c index 58662ba92d4f8..d0ed20652ddb2 100644 --- a/drivers/media/i2c/adv7842.c +++ b/drivers/media/i2c/adv7842.c @@ -3585,7 +3585,7 @@ static int adv7842_remove(struct i2c_client *client) struct adv7842_state *state = to_state(sd); adv7842_irq_enable(sd, false); - cancel_delayed_work(&state->delayed_work_enable_hotplug); + cancel_delayed_work_sync(&state->delayed_work_enable_hotplug); v4l2_device_unregister_subdev(sd); media_entity_cleanup(&sd->entity); adv7842_unregister_clients(sd); diff --git a/drivers/media/i2c/tc358743.c b/drivers/media/i2c/tc358743.c index d9bc3851bf63b..041b16965b967 100644 --- a/drivers/media/i2c/tc358743.c +++ b/drivers/media/i2c/tc358743.c @@ -2192,7 +2192,7 @@ static int tc358743_remove(struct i2c_client *client) del_timer_sync(&state->timer); flush_work(&state->work_i2c_poll); } - cancel_delayed_work(&state->delayed_work_enable_hotplug); + cancel_delayed_work_sync(&state->delayed_work_enable_hotplug); cec_unregister_adapter(state->cec_adap); v4l2_async_unregister_subdev(sd); v4l2_device_unregister_subdev(sd); diff --git a/drivers/media/pci/saa7164/saa7164-encoder.c b/drivers/media/pci/saa7164/saa7164-encoder.c index 32136ebe4f61c..962f8eb73b053 100644 --- a/drivers/media/pci/saa7164/saa7164-encoder.c +++ b/drivers/media/pci/saa7164/saa7164-encoder.c @@ -1024,7 +1024,7 @@ int saa7164_encoder_register(struct saa7164_port *port) printk(KERN_ERR "%s() failed (errno = %d), NO PCI configuration\n", __func__, result); result = -ENOMEM; - goto failed; + goto fail_pci; } /* Establish encoder defaults here */ @@ -1078,7 +1078,7 @@ int saa7164_encoder_register(struct saa7164_port *port) 100000, ENCODER_DEF_BITRATE); if (hdl->error) { result = hdl->error; - goto failed; + goto fail_hdl; } port->std = V4L2_STD_NTSC_M; @@ -1096,7 +1096,7 @@ int saa7164_encoder_register(struct saa7164_port *port) printk(KERN_INFO "%s: can't allocate mpeg device\n", dev->name); result = -ENOMEM; - goto failed; + goto fail_hdl; } port->v4l_device->ctrl_handler = hdl; @@ -1107,10 +1107,7 @@ int saa7164_encoder_register(struct saa7164_port *port) if (result < 0) { printk(KERN_INFO "%s: can't register mpeg device\n", dev->name); - /* TODO: We're going to leak here if we don't dealloc - The buffers above. The unreg function can't deal wit it. - */ - goto failed; + goto fail_reg; } printk(KERN_INFO "%s: registered device video%d [mpeg]\n", @@ -1132,9 +1129,14 @@ int saa7164_encoder_register(struct saa7164_port *port) saa7164_api_set_encoder(port); saa7164_api_get_encoder(port); + return 0; - result = 0; -failed: +fail_reg: + video_device_release(port->v4l_device); + port->v4l_device = NULL; +fail_hdl: + v4l2_ctrl_handler_free(hdl); +fail_pci: return result; } diff --git a/drivers/media/pci/sta2x11/Kconfig b/drivers/media/pci/sta2x11/Kconfig index 4407b9f881e40..bd690613fe68d 100644 --- a/drivers/media/pci/sta2x11/Kconfig +++ b/drivers/media/pci/sta2x11/Kconfig @@ -1,6 +1,7 @@ config STA2X11_VIP tristate "STA2X11 VIP Video For Linux" depends on STA2X11 || COMPILE_TEST + select GPIOLIB if MEDIA_SUBDRV_AUTOSELECT select VIDEO_ADV7180 if MEDIA_SUBDRV_AUTOSELECT select VIDEOBUF2_DMA_CONTIG depends on PCI && VIDEO_V4L2 && VIRT_TO_BUS diff --git a/drivers/media/platform/vivid/vivid-core.c b/drivers/media/platform/vivid/vivid-core.c index 31db363602e53..b603ca412387b 100644 --- a/drivers/media/platform/vivid/vivid-core.c +++ b/drivers/media/platform/vivid/vivid-core.c @@ -174,13 +174,13 @@ static const u8 vivid_hdmi_edid[256] = { 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x01, 0x7b, - 0x02, 0x03, 0x3f, 0xf0, 0x51, 0x61, 0x60, 0x5f, + 0x02, 0x03, 0x3f, 0xf1, 0x51, 0x61, 0x60, 0x5f, 0x5e, 0x5d, 0x10, 0x1f, 0x04, 0x13, 0x22, 0x21, 0x20, 0x05, 0x14, 0x02, 0x11, 0x01, 0x23, 0x09, 0x07, 0x07, 0x83, 0x01, 0x00, 0x00, 0x6d, 0x03, 0x0c, 0x00, 0x10, 0x00, 0x00, 0x3c, 0x21, 0x00, 0x60, 0x01, 0x02, 0x03, 0x67, 0xd8, 0x5d, 0xc4, - 0x01, 0x78, 0x00, 0x00, 0xe2, 0x00, 0xea, 0xe3, + 0x01, 0x78, 0x00, 0x00, 0xe2, 0x00, 0xca, 0xe3, 0x05, 0x00, 0x00, 0xe3, 0x06, 0x01, 0x00, 0x4d, 0xd0, 0x00, 0xa0, 0xf0, 0x70, 0x3e, 0x80, 0x30, 0x20, 0x35, 0x00, 0xc0, 0x1c, 0x32, 0x00, 0x00, @@ -189,7 +189,7 @@ static const u8 vivid_hdmi_edid[256] = { 0x00, 0x00, 0x1a, 0x1a, 0x1d, 0x00, 0x80, 0x51, 0xd0, 0x1c, 0x20, 0x40, 0x80, 0x35, 0x00, 0xc0, 0x1c, 0x32, 0x00, 0x00, 0x1c, 0x00, 0x00, 0x00, - 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x63, + 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x82, }; static int vidioc_querycap(struct file *file, void *priv, diff --git a/drivers/media/platform/vivid/vivid-vid-out.c b/drivers/media/platform/vivid/vivid-vid-out.c index 0f909500a0b80..ecd9e36ef3f63 100644 --- a/drivers/media/platform/vivid/vivid-vid-out.c +++ b/drivers/media/platform/vivid/vivid-vid-out.c @@ -998,7 +998,7 @@ int vivid_vid_out_s_fbuf(struct file *file, void *fh, return -EINVAL; } dev->fbuf_out_flags &= ~(chroma_flags | alpha_flags); - dev->fbuf_out_flags = a->flags & (chroma_flags | alpha_flags); + dev->fbuf_out_flags |= a->flags & (chroma_flags | alpha_flags); return 0; } diff --git a/drivers/media/rc/ite-cir.c b/drivers/media/rc/ite-cir.c index de77d22c30a70..18f3718315a83 100644 --- a/drivers/media/rc/ite-cir.c +++ b/drivers/media/rc/ite-cir.c @@ -285,8 +285,14 @@ static irqreturn_t ite_cir_isr(int irq, void *data) /* read the interrupt flags */ iflags = dev->params.get_irq_causes(dev); + /* Check for RX overflow */ + if (iflags & ITE_IRQ_RX_FIFO_OVERRUN) { + dev_warn(&dev->rdev->dev, "receive overflow\n"); + ir_raw_event_reset(dev->rdev); + } + /* check for the receive interrupt */ - if (iflags & (ITE_IRQ_RX_FIFO | ITE_IRQ_RX_FIFO_OVERRUN)) { + if (iflags & ITE_IRQ_RX_FIFO) { /* read the FIFO bytes */ rx_bytes = dev->params.get_rx_bytes(dev, rx_buf, diff --git a/drivers/media/tuners/m88rs6000t.c b/drivers/media/tuners/m88rs6000t.c index 3df2f23a40beb..3fe13de487771 100644 --- a/drivers/media/tuners/m88rs6000t.c +++ b/drivers/media/tuners/m88rs6000t.c @@ -534,7 +534,7 @@ static int m88rs6000t_get_rf_strength(struct dvb_frontend *fe, u16 *strength) PGA2_cri = PGA2_GC >> 2; PGA2_crf = PGA2_GC & 0x03; - for (i = 0; i <= RF_GC; i++) + for (i = 0; i <= RF_GC && i < ARRAY_SIZE(RFGS); i++) RFG += RFGS[i]; if (RF_GC == 0) @@ -546,12 +546,12 @@ static int m88rs6000t_get_rf_strength(struct dvb_frontend *fe, u16 *strength) if (RF_GC == 3) RFG += 100; - for (i = 0; i <= IF_GC; i++) + for (i = 0; i <= IF_GC && i < ARRAY_SIZE(IFGS); i++) IFG += IFGS[i]; TIAG = TIA_GC * TIA_GS; - for (i = 0; i <= BB_GC; i++) + for (i = 0; i <= BB_GC && i < ARRAY_SIZE(BBGS); i++) BBG += BBGS[i]; PGA2G = PGA2_cri * PGA2_cri_GS + PGA2_crf * PGA2_crf_GS; diff --git a/drivers/media/usb/dvb-usb/dvb-usb-init.c b/drivers/media/usb/dvb-usb/dvb-usb-init.c index 39ac22486bcd9..4b1445d806e5b 100644 --- a/drivers/media/usb/dvb-usb/dvb-usb-init.c +++ b/drivers/media/usb/dvb-usb/dvb-usb-init.c @@ -82,11 +82,17 @@ static int dvb_usb_adapter_init(struct dvb_usb_device *d, short *adapter_nrs) } } - if ((ret = dvb_usb_adapter_stream_init(adap)) || - (ret = dvb_usb_adapter_dvb_init(adap, adapter_nrs)) || - (ret = dvb_usb_adapter_frontend_init(adap))) { + ret = dvb_usb_adapter_stream_init(adap); + if (ret) return ret; - } + + ret = dvb_usb_adapter_dvb_init(adap, adapter_nrs); + if (ret) + goto dvb_init_err; + + ret = dvb_usb_adapter_frontend_init(adap); + if (ret) + goto frontend_init_err; /* use exclusive FE lock if there is multiple shared FEs */ if (adap->fe_adap[1].fe) @@ -106,6 +112,12 @@ static int dvb_usb_adapter_init(struct dvb_usb_device *d, short *adapter_nrs) } return 0; + +frontend_init_err: + dvb_usb_adapter_dvb_exit(adap); +dvb_init_err: + dvb_usb_adapter_stream_exit(adap); + return ret; } static int dvb_usb_adapter_exit(struct dvb_usb_device *d) diff --git a/drivers/media/usb/dvb-usb/dvb-usb.h b/drivers/media/usb/dvb-usb/dvb-usb.h index 317ed6a82d194..89702eef66aa0 100644 --- a/drivers/media/usb/dvb-usb/dvb-usb.h +++ b/drivers/media/usb/dvb-usb/dvb-usb.h @@ -475,7 +475,7 @@ extern int __must_check dvb_usb_generic_write(struct dvb_usb_device *, u8 *, u16); /* commonly used remote control parsing */ -extern int dvb_usb_nec_rc_key_to_event(struct dvb_usb_device *, u8[], u32 *, int *); +extern int dvb_usb_nec_rc_key_to_event(struct dvb_usb_device *, u8[5], u32 *, int *); /* commonly used firmware download types and function */ struct hexline { diff --git a/drivers/media/usb/em28xx/em28xx-dvb.c b/drivers/media/usb/em28xx/em28xx-dvb.c index a73faf12f7e47..e1946237ac8cd 100644 --- a/drivers/media/usb/em28xx/em28xx-dvb.c +++ b/drivers/media/usb/em28xx/em28xx-dvb.c @@ -1924,6 +1924,7 @@ ret: return result; out_free: + em28xx_uninit_usb_xfer(dev, EM28XX_DIGITAL_MODE); kfree(dvb); dev->dvb = NULL; goto ret; diff --git a/drivers/media/usb/gspca/gspca.c b/drivers/media/usb/gspca/gspca.c index 93212ed80bf85..f0562b8eef562 100644 --- a/drivers/media/usb/gspca/gspca.c +++ b/drivers/media/usb/gspca/gspca.c @@ -1586,6 +1586,8 @@ out: #endif v4l2_ctrl_handler_free(gspca_dev->vdev.ctrl_handler); v4l2_device_unregister(&gspca_dev->v4l2_dev); + if (sd_desc->probe_error) + sd_desc->probe_error(gspca_dev); kfree(gspca_dev->usb_buf); kfree(gspca_dev); return ret; diff --git a/drivers/media/usb/gspca/gspca.h b/drivers/media/usb/gspca/gspca.h index b0ced2e140064..a6554d5e9e1a5 100644 --- a/drivers/media/usb/gspca/gspca.h +++ b/drivers/media/usb/gspca/gspca.h @@ -105,6 +105,7 @@ struct sd_desc { cam_cf_op config; /* called on probe */ cam_op init; /* called on probe and resume */ cam_op init_controls; /* called on probe */ + cam_v_op probe_error; /* called if probe failed, do cleanup here */ cam_op start; /* called on stream on after URBs creation */ cam_pkt_op pkt_scan; /* optional operations */ diff --git a/drivers/media/usb/gspca/sq905.c b/drivers/media/usb/gspca/sq905.c index ffea9c35b0a06..13676af42cfc7 100644 --- a/drivers/media/usb/gspca/sq905.c +++ b/drivers/media/usb/gspca/sq905.c @@ -167,7 +167,7 @@ static int sq905_read_data(struct gspca_dev *gspca_dev, u8 *data, int size, int need_lock) { int ret; - int act_len; + int act_len = 0; gspca_dev->usb_buf[0] = '\0'; if (need_lock) diff --git a/drivers/media/usb/gspca/stv06xx/stv06xx.c b/drivers/media/usb/gspca/stv06xx/stv06xx.c index b7ea4f9829648..ccec6138f6789 100644 --- a/drivers/media/usb/gspca/stv06xx/stv06xx.c +++ b/drivers/media/usb/gspca/stv06xx/stv06xx.c @@ -538,12 +538,21 @@ static int sd_int_pkt_scan(struct gspca_dev *gspca_dev, static int stv06xx_config(struct gspca_dev *gspca_dev, const struct usb_device_id *id); +static void stv06xx_probe_error(struct gspca_dev *gspca_dev) +{ + struct sd *sd = (struct sd *)gspca_dev; + + kfree(sd->sensor_priv); + sd->sensor_priv = NULL; +} + /* sub-driver description */ static const struct sd_desc sd_desc = { .name = MODULE_NAME, .config = stv06xx_config, .init = stv06xx_init, .init_controls = stv06xx_init_controls, + .probe_error = stv06xx_probe_error, .start = stv06xx_start, .stopN = stv06xx_stopN, .pkt_scan = stv06xx_pkt_scan, diff --git a/drivers/memory/omap-gpmc.c b/drivers/memory/omap-gpmc.c index 2ca507f3a58c3..d8f2cacea750d 100644 --- a/drivers/memory/omap-gpmc.c +++ b/drivers/memory/omap-gpmc.c @@ -1028,8 +1028,8 @@ EXPORT_SYMBOL(gpmc_cs_request); void gpmc_cs_free(int cs) { - struct gpmc_cs_data *gpmc = &gpmc_cs[cs]; - struct resource *res = &gpmc->mem; + struct gpmc_cs_data *gpmc; + struct resource *res; spin_lock(&gpmc_mem_lock); if (cs >= gpmc_cs_num || cs < 0 || !gpmc_cs_reserved(cs)) { @@ -1038,6 +1038,9 @@ void gpmc_cs_free(int cs) spin_unlock(&gpmc_mem_lock); return; } + gpmc = &gpmc_cs[cs]; + res = &gpmc->mem; + gpmc_cs_disable_mem(cs); if (res->flags) release_resource(res); diff --git a/drivers/mfd/stm32-timers.c b/drivers/mfd/stm32-timers.c index efcd4b980c94c..1adba6a46dcb1 100644 --- a/drivers/mfd/stm32-timers.c +++ b/drivers/mfd/stm32-timers.c @@ -158,13 +158,18 @@ static const struct regmap_config stm32_timers_regmap_cfg = { static void stm32_timers_get_arr_size(struct stm32_timers *ddata) { + u32 arr; + + /* Backup ARR to restore it after getting the maximum value */ + regmap_read(ddata->regmap, TIM_ARR, &arr); + /* * Only the available bits will be written so when readback * we get the maximum value of auto reload register */ regmap_write(ddata->regmap, TIM_ARR, ~0L); regmap_read(ddata->regmap, TIM_ARR, &ddata->max_arr); - regmap_write(ddata->regmap, TIM_ARR, 0x0); + regmap_write(ddata->regmap, TIM_ARR, arr); } static void stm32_timers_dma_probe(struct device *dev, diff --git a/drivers/misc/aspeed-lpc-snoop.c b/drivers/misc/aspeed-lpc-snoop.c index b4a776bf44bc5..e2cb0b9607d11 100644 --- a/drivers/misc/aspeed-lpc-snoop.c +++ b/drivers/misc/aspeed-lpc-snoop.c @@ -99,8 +99,10 @@ static ssize_t snoop_file_read(struct file *file, char __user *buffer, return -EINTR; } ret = kfifo_to_user(&chan->fifo, buffer, count, &copied); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static __poll_t snoop_file_poll(struct file *file, diff --git a/drivers/misc/kgdbts.c b/drivers/misc/kgdbts.c index 8b01257783dd8..f2cfc96194250 100644 --- a/drivers/misc/kgdbts.c +++ b/drivers/misc/kgdbts.c @@ -107,19 +107,19 @@ #include -#define v1printk(a...) do { \ - if (verbose) \ - printk(KERN_INFO a); \ - } while (0) -#define v2printk(a...) do { \ - if (verbose > 1) \ - printk(KERN_INFO a); \ - touch_nmi_watchdog(); \ - } while (0) -#define eprintk(a...) do { \ - printk(KERN_ERR a); \ - WARN_ON(1); \ - } while (0) +#define v1printk(a...) do { \ + if (verbose) \ + printk(KERN_INFO a); \ +} while (0) +#define v2printk(a...) do { \ + if (verbose > 1) \ + printk(KERN_INFO a); \ + touch_nmi_watchdog(); \ +} while (0) +#define eprintk(a...) do { \ + printk(KERN_ERR a); \ + WARN_ON(1); \ +} while (0) #define MAX_CONFIG_LEN 40 static struct kgdb_io kgdbts_io_ops; diff --git a/drivers/misc/lis3lv02d/lis3lv02d.c b/drivers/misc/lis3lv02d/lis3lv02d.c index e9bb1cfa6a7a2..21ac34b383950 100644 --- a/drivers/misc/lis3lv02d/lis3lv02d.c +++ b/drivers/misc/lis3lv02d/lis3lv02d.c @@ -221,7 +221,7 @@ static int lis3_3dc_rates[16] = {0, 1, 10, 25, 50, 100, 200, 400, 1600, 5000}; static int lis3_3dlh_rates[4] = {50, 100, 400, 1000}; /* ODR is Output Data Rate */ -static int lis3lv02d_get_odr(struct lis3lv02d *lis3) +static int lis3lv02d_get_odr_index(struct lis3lv02d *lis3) { u8 ctrl; int shift; @@ -229,15 +229,23 @@ static int lis3lv02d_get_odr(struct lis3lv02d *lis3) lis3->read(lis3, CTRL_REG1, &ctrl); ctrl &= lis3->odr_mask; shift = ffs(lis3->odr_mask) - 1; - return lis3->odrs[(ctrl >> shift)]; + return (ctrl >> shift); } static int lis3lv02d_get_pwron_wait(struct lis3lv02d *lis3) { - int div = lis3lv02d_get_odr(lis3); + int odr_idx = lis3lv02d_get_odr_index(lis3); + int div = lis3->odrs[odr_idx]; - if (WARN_ONCE(div == 0, "device returned spurious data")) + if (div == 0) { + if (odr_idx == 0) { + /* Power-down mode, not sampling no need to sleep */ + return 0; + } + + dev_err(&lis3->pdev->dev, "Error unknown odrs-index: %d\n", odr_idx); return -ENXIO; + } /* LIS3 power on delay is quite long */ msleep(lis3->pwron_delay / div); @@ -820,9 +828,12 @@ static ssize_t lis3lv02d_rate_show(struct device *dev, struct device_attribute *attr, char *buf) { struct lis3lv02d *lis3 = dev_get_drvdata(dev); + int odr_idx; lis3lv02d_sysfs_poweron(lis3); - return sprintf(buf, "%d\n", lis3lv02d_get_odr(lis3)); + + odr_idx = lis3lv02d_get_odr_index(lis3); + return sprintf(buf, "%d\n", lis3->odrs[odr_idx]); } static ssize_t lis3lv02d_rate_set(struct device *dev, diff --git a/drivers/misc/vmw_vmci/vmci_doorbell.c b/drivers/misc/vmw_vmci/vmci_doorbell.c index f005206d9033b..4581210349d29 100644 --- a/drivers/misc/vmw_vmci/vmci_doorbell.c +++ b/drivers/misc/vmw_vmci/vmci_doorbell.c @@ -334,7 +334,7 @@ int vmci_dbell_host_context_notify(u32 src_cid, struct vmci_handle handle) bool vmci_dbell_register_notification_bitmap(u32 bitmap_ppn) { int result; - struct vmci_notify_bm_set_msg bitmap_set_msg; + struct vmci_notify_bm_set_msg bitmap_set_msg = { }; bitmap_set_msg.hdr.dst = vmci_make_handle(VMCI_HYPERVISOR_CONTEXT_ID, VMCI_SET_NOTIFY_BITMAP); diff --git a/drivers/misc/vmw_vmci/vmci_guest.c b/drivers/misc/vmw_vmci/vmci_guest.c index dad5abee656ef..dd20ea4ad0c47 100644 --- a/drivers/misc/vmw_vmci/vmci_guest.c +++ b/drivers/misc/vmw_vmci/vmci_guest.c @@ -169,7 +169,7 @@ static int vmci_check_host_caps(struct pci_dev *pdev) VMCI_UTIL_NUM_RESOURCES * sizeof(u32); struct vmci_datagram *check_msg; - check_msg = kmalloc(msg_size, GFP_KERNEL); + check_msg = kzalloc(msg_size, GFP_KERNEL); if (!check_msg) { dev_err(&pdev->dev, "%s: Insufficient memory\n", __func__); return -ENOMEM; diff --git a/drivers/mmc/core/block.c b/drivers/mmc/core/block.c index 77324ea4eb93e..c2c45c148ae76 100644 --- a/drivers/mmc/core/block.c +++ b/drivers/mmc/core/block.c @@ -622,6 +622,18 @@ static int __mmc_blk_ioctl_cmd(struct mmc_card *card, struct mmc_blk_data *md, main_md->part_curr = value & EXT_CSD_PART_CONFIG_ACC_MASK; } + /* + * Make sure to update CACHE_CTRL in case it was changed. The cache + * will get turned back on if the card is re-initialized, e.g. + * suspend/resume or hw reset in recovery. + */ + if ((MMC_EXTRACT_INDEX_FROM_ARG(cmd.arg) == EXT_CSD_CACHE_CTRL) && + (cmd.opcode == MMC_SWITCH)) { + u8 value = MMC_EXTRACT_VALUE_FROM_ARG(cmd.arg) & 1; + + card->ext_csd.cache_ctrl = value; + } + /* * According to the SD specs, some commands require a delay after * issuing the command. @@ -2224,6 +2236,10 @@ enum mmc_issued mmc_blk_mq_issue_rq(struct mmc_queue *mq, struct request *req) case MMC_ISSUE_ASYNC: switch (req_op(req)) { case REQ_OP_FLUSH: + if (!mmc_cache_enabled(host)) { + blk_mq_end_request(req, BLK_STS_OK); + return MMC_REQ_FINISHED; + } ret = mmc_blk_cqe_issue_flush(mq, req); break; case REQ_OP_READ: diff --git a/drivers/mmc/core/core.c b/drivers/mmc/core/core.c index 56f7f3600469a..798bcb65b4df4 100644 --- a/drivers/mmc/core/core.c +++ b/drivers/mmc/core/core.c @@ -1537,7 +1537,7 @@ int mmc_set_uhs_voltage(struct mmc_host *host, u32 ocr) err = mmc_wait_for_cmd(host, &cmd, 0); if (err) - return err; + goto power_cycle; if (!mmc_host_is_spi(host) && (cmd.resp[0] & R1_ERROR)) return -EIO; diff --git a/drivers/mmc/core/core.h b/drivers/mmc/core/core.h index 087ba68b29209..3071b644e94a6 100644 --- a/drivers/mmc/core/core.h +++ b/drivers/mmc/core/core.h @@ -32,6 +32,7 @@ struct mmc_bus_ops { int (*shutdown)(struct mmc_host *); int (*hw_reset)(struct mmc_host *); int (*sw_reset)(struct mmc_host *); + bool (*cache_enabled)(struct mmc_host *); }; void mmc_attach_bus(struct mmc_host *host, const struct mmc_bus_ops *ops); @@ -173,4 +174,12 @@ static inline void mmc_post_req(struct mmc_host *host, struct mmc_request *mrq, host->ops->post_req(host, mrq, err); } +static inline bool mmc_cache_enabled(struct mmc_host *host) +{ + if (host->bus_ops->cache_enabled) + return host->bus_ops->cache_enabled(host); + + return false; +} + #endif diff --git a/drivers/mmc/core/mmc.c b/drivers/mmc/core/mmc.c index 1b5139a906b83..d9202f2726d1a 100644 --- a/drivers/mmc/core/mmc.c +++ b/drivers/mmc/core/mmc.c @@ -2009,6 +2009,12 @@ static void mmc_detect(struct mmc_host *host) } } +static bool _mmc_cache_enabled(struct mmc_host *host) +{ + return host->card->ext_csd.cache_size > 0 && + host->card->ext_csd.cache_ctrl & 1; +} + static int _mmc_suspend(struct mmc_host *host, bool is_suspend) { int err = 0; @@ -2193,6 +2199,7 @@ static const struct mmc_bus_ops mmc_ops = { .alive = mmc_alive, .shutdown = mmc_shutdown, .hw_reset = _mmc_hw_reset, + .cache_enabled = _mmc_cache_enabled, }; /* diff --git a/drivers/mmc/core/mmc_ops.c b/drivers/mmc/core/mmc_ops.c index 693b99eff74b5..334678707deb7 100644 --- a/drivers/mmc/core/mmc_ops.c +++ b/drivers/mmc/core/mmc_ops.c @@ -1014,9 +1014,7 @@ int mmc_flush_cache(struct mmc_card *card) { int err = 0; - if (mmc_card_mmc(card) && - (card->ext_csd.cache_size > 0) && - (card->ext_csd.cache_ctrl & 1)) { + if (mmc_cache_enabled(card->host)) { err = mmc_switch(card, EXT_CSD_CMD_SET_NORMAL, EXT_CSD_FLUSH_CACHE, 1, 0); if (err) diff --git a/drivers/mmc/core/sd.c b/drivers/mmc/core/sd.c index 04738359ec029..aa3de584b90cd 100644 --- a/drivers/mmc/core/sd.c +++ b/drivers/mmc/core/sd.c @@ -138,6 +138,9 @@ static int mmc_decode_csd(struct mmc_card *card) csd->erase_size = UNSTUFF_BITS(resp, 39, 7) + 1; csd->erase_size <<= csd->write_blkbits - 9; } + + if (UNSTUFF_BITS(resp, 13, 1)) + mmc_card_set_readonly(card); break; case 1: /* @@ -172,6 +175,9 @@ static int mmc_decode_csd(struct mmc_card *card) csd->write_blkbits = 9; csd->write_partial = 0; csd->erase_size = 1; + + if (UNSTUFF_BITS(resp, 13, 1)) + mmc_card_set_readonly(card); break; default: pr_err("%s: unrecognised CSD structure version %d\n", diff --git a/drivers/mmc/host/sdhci-pci-core.c b/drivers/mmc/host/sdhci-pci-core.c index a411300f9d6dc..cb4a0458f098c 100644 --- a/drivers/mmc/host/sdhci-pci-core.c +++ b/drivers/mmc/host/sdhci-pci-core.c @@ -465,6 +465,7 @@ struct intel_host { int drv_strength; bool d3_retune; bool rpm_retune_ok; + bool needs_pwr_off; u32 glk_rx_ctrl1; u32 glk_tun_val; }; @@ -590,9 +591,25 @@ out: static void sdhci_intel_set_power(struct sdhci_host *host, unsigned char mode, unsigned short vdd) { + struct sdhci_pci_slot *slot = sdhci_priv(host); + struct intel_host *intel_host = sdhci_pci_priv(slot); int cntr; u8 reg; + /* + * Bus power may control card power, but a full reset still may not + * reset the power, whereas a direct write to SDHCI_POWER_CONTROL can. + * That might be needed to initialize correctly, if the card was left + * powered on previously. + */ + if (intel_host->needs_pwr_off) { + intel_host->needs_pwr_off = false; + if (mode != MMC_POWER_OFF) { + sdhci_writeb(host, 0, SDHCI_POWER_CONTROL); + usleep_range(10000, 12500); + } + } + sdhci_set_power(host, mode, vdd); if (mode == MMC_POWER_OFF) @@ -926,6 +943,14 @@ static int byt_sdio_probe_slot(struct sdhci_pci_slot *slot) return 0; } +static void byt_needs_pwr_off(struct sdhci_pci_slot *slot) +{ + struct intel_host *intel_host = sdhci_pci_priv(slot); + u8 reg = sdhci_readb(slot->host, SDHCI_POWER_CONTROL); + + intel_host->needs_pwr_off = reg & SDHCI_POWER_ON; +} + static int byt_sd_probe_slot(struct sdhci_pci_slot *slot) { byt_probe_slot(slot); @@ -943,6 +968,8 @@ static int byt_sd_probe_slot(struct sdhci_pci_slot *slot) slot->chip->pdev->subsystem_device == PCI_SUBDEVICE_ID_NI_78E3) slot->host->mmc->caps2 |= MMC_CAP2_AVOID_3_3V; + byt_needs_pwr_off(slot); + return 0; } diff --git a/drivers/mtd/mtdchar.c b/drivers/mtd/mtdchar.c index 5afc653c09e20..82d38001d5175 100644 --- a/drivers/mtd/mtdchar.c +++ b/drivers/mtd/mtdchar.c @@ -663,16 +663,12 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg) 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: @@ -683,9 +679,13 @@ static int mtdchar_ioctl(struct file *file, u_int cmd, u_long arg) /* "dangerous" commands */ case MEMERASE: case MEMERASE64: + case MEMLOCK: + case MEMUNLOCK: + case MEMSETBADBLOCK: case MEMWRITEOOB: case MEMWRITEOOB64: case MEMWRITE: + case OTPLOCK: if (!(file->f_mode & FMODE_WRITE)) return -EPERM; break; diff --git a/drivers/mtd/mtdcore.c b/drivers/mtd/mtdcore.c index 97ac219c082e7..a0b1a7814e2e7 100644 --- a/drivers/mtd/mtdcore.c +++ b/drivers/mtd/mtdcore.c @@ -712,6 +712,9 @@ int mtd_device_parse_register(struct mtd_info *mtd, const char * const *types, /* Prefer parsed partitions over driver-provided fallback */ ret = parse_mtd_partitions(mtd, types, parser_data); + if (ret == -EPROBE_DEFER) + goto out; + if (ret > 0) ret = 0; else if (nr_parts) diff --git a/drivers/mtd/nand/raw/atmel/nand-controller.c b/drivers/mtd/nand/raw/atmel/nand-controller.c index ee1c401f131f4..7887629304872 100644 --- a/drivers/mtd/nand/raw/atmel/nand-controller.c +++ b/drivers/mtd/nand/raw/atmel/nand-controller.c @@ -826,10 +826,12 @@ static int atmel_nand_pmecc_correct_data(struct nand_chip *chip, void *buf, NULL, 0, chip->ecc.strength); - if (ret >= 0) + if (ret >= 0) { + mtd->ecc_stats.corrected += ret; max_bitflips = max(ret, max_bitflips); - else + } else { mtd->ecc_stats.failed++; + } databuf += chip->ecc.size; eccbuf += chip->ecc.bytes; diff --git a/drivers/mtd/nand/raw/brcmnand/brcmnand.c b/drivers/mtd/nand/raw/brcmnand/brcmnand.c index aad8d107b85d2..774ffa9e23f38 100644 --- a/drivers/mtd/nand/raw/brcmnand/brcmnand.c +++ b/drivers/mtd/nand/raw/brcmnand/brcmnand.c @@ -2239,6 +2239,12 @@ static int brcmnand_attach_chip(struct nand_chip *chip) ret = brcmstb_choose_ecc_layout(host); + /* If OOB is written with ECC enabled it will cause ECC errors */ + if (is_hamming_ecc(host->ctrl, &host->hwcfg)) { + chip->ecc.write_oob = brcmnand_write_oob_raw; + chip->ecc.read_oob = brcmnand_read_oob_raw; + } + return ret; } diff --git a/drivers/mtd/nand/raw/fsmc_nand.c b/drivers/mtd/nand/raw/fsmc_nand.c index 25d354e9448ec..a31bb1da44ec9 100644 --- a/drivers/mtd/nand/raw/fsmc_nand.c +++ b/drivers/mtd/nand/raw/fsmc_nand.c @@ -1099,11 +1099,13 @@ static int __init fsmc_nand_probe(struct platform_device *pdev) host->read_dma_chan = dma_request_channel(mask, filter, NULL); if (!host->read_dma_chan) { dev_err(&pdev->dev, "Unable to get read dma channel\n"); + ret = -ENODEV; goto disable_clk; } host->write_dma_chan = dma_request_channel(mask, filter, NULL); if (!host->write_dma_chan) { dev_err(&pdev->dev, "Unable to get write dma channel\n"); + ret = -ENODEV; goto release_dma_read_chan; } } diff --git a/drivers/mtd/nand/raw/gpmi-nand/gpmi-nand.c b/drivers/mtd/nand/raw/gpmi-nand/gpmi-nand.c index fe99d9323d4ac..6bd414bac34d1 100644 --- a/drivers/mtd/nand/raw/gpmi-nand/gpmi-nand.c +++ b/drivers/mtd/nand/raw/gpmi-nand/gpmi-nand.c @@ -1931,7 +1931,7 @@ static int gpmi_nand_init(struct gpmi_nand_data *this) this->bch_geometry.auxiliary_size = 128; ret = gpmi_alloc_dma_buffer(this); if (ret) - goto err_out; + return ret; chip->dummy_controller.ops = &gpmi_nand_controller_ops; ret = nand_scan(chip, GPMI_IS_MX6(this) ? 2 : 1); diff --git a/drivers/mtd/nand/raw/qcom_nandc.c b/drivers/mtd/nand/raw/qcom_nandc.c index 2726f18242333..148c7a16f3188 100644 --- a/drivers/mtd/nand/raw/qcom_nandc.c +++ b/drivers/mtd/nand/raw/qcom_nandc.c @@ -2865,7 +2865,7 @@ static int qcom_probe_nand_devices(struct qcom_nand_controller *nandc) struct device *dev = nandc->dev; struct device_node *dn = dev->of_node, *child; struct qcom_nand_host *host; - int ret; + int ret = -ENODEV; for_each_available_child_of_node(dn, child) { host = devm_kzalloc(dev, sizeof(*host), GFP_KERNEL); @@ -2883,10 +2883,7 @@ static int qcom_probe_nand_devices(struct qcom_nand_controller *nandc) list_add_tail(&host->node, &nandc->host_list); } - if (list_empty(&nandc->host_list)) - return -ENODEV; - - return 0; + return ret; } /* parse custom DT properties here */ diff --git a/drivers/mtd/nand/spi/core.c b/drivers/mtd/nand/spi/core.c index 1d61ae7aaa66c..4a3dc5953b002 100644 --- a/drivers/mtd/nand/spi/core.c +++ b/drivers/mtd/nand/spi/core.c @@ -1129,12 +1129,14 @@ static const struct spi_device_id spinand_ids[] = { { .name = "spi-nand" }, { /* sentinel */ }, }; +MODULE_DEVICE_TABLE(spi, spinand_ids); #ifdef CONFIG_OF static const struct of_device_id spinand_of_ids[] = { { .compatible = "spi-nand" }, { /* sentinel */ }, }; +MODULE_DEVICE_TABLE(of, spinand_of_ids); #endif static struct spi_mem_driver spinand_drv = { diff --git a/drivers/net/ethernet/broadcom/bnxt/bnxt.c b/drivers/net/ethernet/broadcom/bnxt/bnxt.c index 44ed2f6e2d96c..6033970fb667b 100644 --- a/drivers/net/ethernet/broadcom/bnxt/bnxt.c +++ b/drivers/net/ethernet/broadcom/bnxt/bnxt.c @@ -6851,7 +6851,9 @@ static ssize_t bnxt_show_temp(struct device *dev, if (!rc) len = sprintf(buf, "%u\n", resp->temp * 1000); /* display millidegree */ mutex_unlock(&bp->hwrm_cmd_lock); - return rc ?: len; + if (rc) + return rc; + return len; } static SENSOR_DEVICE_ATTR(temp1_input, 0444, bnxt_show_temp, NULL, 0); diff --git a/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_regs.h b/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_regs.h index e6d4ad99cc387..3f1c189646f4e 100644 --- a/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_regs.h +++ b/drivers/net/ethernet/cavium/liquidio/cn23xx_pf_regs.h @@ -521,7 +521,7 @@ #define CN23XX_BAR1_INDEX_OFFSET 3 #define CN23XX_PEM_BAR1_INDEX_REG(port, idx) \ - (CN23XX_PEM_BAR1_INDEX_START + ((port) << CN23XX_PEM_OFFSET) + \ + (CN23XX_PEM_BAR1_INDEX_START + (((u64)port) << CN23XX_PEM_OFFSET) + \ ((idx) << CN23XX_BAR1_INDEX_OFFSET)) /*############################ DPI #########################*/ diff --git a/drivers/net/ethernet/cavium/thunder/nicvf_queues.c b/drivers/net/ethernet/cavium/thunder/nicvf_queues.c index 9a4cfa61ed93a..d9bcbe469ab98 100644 --- a/drivers/net/ethernet/cavium/thunder/nicvf_queues.c +++ b/drivers/net/ethernet/cavium/thunder/nicvf_queues.c @@ -779,7 +779,7 @@ static void nicvf_rcv_queue_config(struct nicvf *nic, struct queue_set *qs, mbx.rq.msg = NIC_MBOX_MSG_RQ_CFG; mbx.rq.qs_num = qs->vnic_id; mbx.rq.rq_num = qidx; - mbx.rq.cfg = (rq->caching << 26) | (rq->cq_qs << 19) | + mbx.rq.cfg = ((u64)rq->caching << 26) | (rq->cq_qs << 19) | (rq->cq_idx << 16) | (rq->cont_rbdr_qs << 9) | (rq->cont_qs_rbdr_idx << 8) | (rq->start_rbdr_qs << 1) | (rq->start_qs_rbdr_idx); diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_debugfs.c b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_debugfs.c index 4af6e6ffc5df2..3caf8bd1e00e7 100644 --- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_debugfs.c +++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_debugfs.c @@ -2730,7 +2730,7 @@ do { \ seq_printf(seq, "%-12s", s); \ for (i = 0; i < n; ++i) \ seq_printf(seq, " %16" fmt_spec, v); \ - seq_putc(seq, '\n'); \ + seq_putc(seq, '\n'); \ } while (0) #define S(s, v) S3("s", s, v) #define T3(fmt_spec, s, v) S3(fmt_spec, s, tx[i].v) diff --git a/drivers/net/ethernet/cisco/enic/enic_main.c b/drivers/net/ethernet/cisco/enic/enic_main.c index 810cbe2210463..bfe0e820956ca 100644 --- a/drivers/net/ethernet/cisco/enic/enic_main.c +++ b/drivers/net/ethernet/cisco/enic/enic_main.c @@ -803,7 +803,7 @@ static inline int enic_queue_wq_skb_encap(struct enic *enic, struct vnic_wq *wq, return err; } -static inline void enic_queue_wq_skb(struct enic *enic, +static inline int enic_queue_wq_skb(struct enic *enic, struct vnic_wq *wq, struct sk_buff *skb) { unsigned int mss = skb_shinfo(skb)->gso_size; @@ -849,6 +849,7 @@ static inline void enic_queue_wq_skb(struct enic *enic, wq->to_use = buf->next; dev_kfree_skb(skb); } + return err; } /* netif_tx_lock held, process context with BHs disabled, or BH */ @@ -892,7 +893,8 @@ static netdev_tx_t enic_hard_start_xmit(struct sk_buff *skb, return NETDEV_TX_BUSY; } - enic_queue_wq_skb(enic, wq, skb); + if (enic_queue_wq_skb(enic, wq, skb)) + goto error; if (vnic_wq_desc_avail(wq) < MAX_SKB_FRAGS + ENIC_DESC_MAX_SPLITS) netif_tx_stop_queue(txq); @@ -900,6 +902,7 @@ static netdev_tx_t enic_hard_start_xmit(struct sk_buff *skb, if (!skb->xmit_more || netif_xmit_stopped(txq)) vnic_wq_doorbell(wq); +error: spin_unlock(&enic->wq_lock[txq_map]); return NETDEV_TX_OK; diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c index 3eb8b85f6afb6..3b89673f09daf 100644 --- a/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c +++ b/drivers/net/ethernet/hisilicon/hns3/hns3_enet.c @@ -2639,7 +2639,6 @@ static void hns3_add_ring_to_group(struct hns3_enet_ring_group *group, static int hns3_nic_init_vector_data(struct hns3_nic_priv *priv) { - struct hnae3_ring_chain_node vector_ring_chain; struct hnae3_handle *h = priv->ae_handle; struct hns3_enet_tqp_vector *tqp_vector; int ret = 0; @@ -2669,6 +2668,8 @@ static int hns3_nic_init_vector_data(struct hns3_nic_priv *priv) } for (i = 0; i < priv->vector_num; i++) { + struct hnae3_ring_chain_node vector_ring_chain; + tqp_vector = &priv->tqp_vector[i]; tqp_vector->rx_group.total_bytes = 0; diff --git a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c index 03491e8ebb730..d0fa344f0a84f 100644 --- a/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c +++ b/drivers/net/ethernet/hisilicon/hns3/hns3pf/hclge_mdio.c @@ -235,6 +235,8 @@ void hclge_mac_start_phy(struct hclge_dev *hdev) if (!phydev) return; + phy_loopback(phydev, false); + phy_start(phydev); } diff --git a/drivers/net/ethernet/intel/i40e/i40e_client.c b/drivers/net/ethernet/intel/i40e/i40e_client.c index 5f3b8b9ff511d..c1832a8487140 100644 --- a/drivers/net/ethernet/intel/i40e/i40e_client.c +++ b/drivers/net/ethernet/intel/i40e/i40e_client.c @@ -377,6 +377,7 @@ void i40e_client_subtask(struct i40e_pf *pf) clear_bit(__I40E_CLIENT_INSTANCE_OPENED, &cdev->state); i40e_client_del_instance(pf); + return; } } } diff --git a/drivers/net/ethernet/mediatek/mtk_eth_soc.c b/drivers/net/ethernet/mediatek/mtk_eth_soc.c index b72a4fad7bc8f..59f3dce3ab1d9 100644 --- a/drivers/net/ethernet/mediatek/mtk_eth_soc.c +++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.c @@ -1041,7 +1041,7 @@ static int mtk_poll_rx(struct napi_struct *napi, int budget, skb->protocol = eth_type_trans(skb, netdev); if (netdev->features & NETIF_F_HW_VLAN_CTAG_RX && - RX_DMA_VID(trxd.rxd3)) + (trxd.rxd2 & RX_DMA_VTAG)) __vlan_hwaccel_put_tag(skb, htons(ETH_P_8021Q), RX_DMA_VID(trxd.rxd3)); skb_record_rx_queue(skb, 0); diff --git a/drivers/net/ethernet/mediatek/mtk_eth_soc.h b/drivers/net/ethernet/mediatek/mtk_eth_soc.h index 46819297fc3ed..cb6b27861afa5 100644 --- a/drivers/net/ethernet/mediatek/mtk_eth_soc.h +++ b/drivers/net/ethernet/mediatek/mtk_eth_soc.h @@ -285,6 +285,7 @@ #define RX_DMA_DONE BIT(31) #define RX_DMA_PLEN0(_x) (((_x) & 0x3fff) << 16) #define RX_DMA_GET_PLEN0(_x) (((_x) >> 16) & 0x3fff) +#define RX_DMA_VTAG BIT(15) /* QDMA descriptor rxd3 */ #define RX_DMA_VID(_x) ((_x) & 0xfff) diff --git a/drivers/net/ethernet/mellanox/mlxsw/spectrum_mr.c b/drivers/net/ethernet/mellanox/mlxsw/spectrum_mr.c index 336e5ecc68f86..f1874578aa141 100644 --- a/drivers/net/ethernet/mellanox/mlxsw/spectrum_mr.c +++ b/drivers/net/ethernet/mellanox/mlxsw/spectrum_mr.c @@ -524,6 +524,16 @@ mlxsw_sp_mr_route_evif_resolve(struct mlxsw_sp_mr_table *mr_table, u16 erif_index = 0; int err; + /* Add the eRIF */ + if (mlxsw_sp_mr_vif_valid(rve->mr_vif)) { + erif_index = mlxsw_sp_rif_index(rve->mr_vif->rif); + err = mr->mr_ops->route_erif_add(mlxsw_sp, + rve->mr_route->route_priv, + erif_index); + if (err) + return err; + } + /* Update the route action, as the new eVIF can be a tunnel or a pimreg * device which will require updating the action. */ @@ -533,17 +543,7 @@ mlxsw_sp_mr_route_evif_resolve(struct mlxsw_sp_mr_table *mr_table, rve->mr_route->route_priv, route_action); if (err) - return err; - } - - /* Add the eRIF */ - if (mlxsw_sp_mr_vif_valid(rve->mr_vif)) { - erif_index = mlxsw_sp_rif_index(rve->mr_vif->rif); - err = mr->mr_ops->route_erif_add(mlxsw_sp, - rve->mr_route->route_priv, - erif_index); - if (err) - goto err_route_erif_add; + goto err_route_action_update; } /* Update the minimum MTU */ @@ -561,14 +561,14 @@ mlxsw_sp_mr_route_evif_resolve(struct mlxsw_sp_mr_table *mr_table, return 0; err_route_min_mtu_update: - if (mlxsw_sp_mr_vif_valid(rve->mr_vif)) - mr->mr_ops->route_erif_del(mlxsw_sp, rve->mr_route->route_priv, - erif_index); -err_route_erif_add: if (route_action != rve->mr_route->route_action) mr->mr_ops->route_action_update(mlxsw_sp, rve->mr_route->route_priv, rve->mr_route->route_action); +err_route_action_update: + if (mlxsw_sp_mr_vif_valid(rve->mr_vif)) + mr->mr_ops->route_erif_del(mlxsw_sp, rve->mr_route->route_priv, + erif_index); return err; } diff --git a/drivers/net/ethernet/qualcomm/emac/emac-mac.c b/drivers/net/ethernet/qualcomm/emac/emac-mac.c index 031f6e6ee9c17..351a906980103 100644 --- a/drivers/net/ethernet/qualcomm/emac/emac-mac.c +++ b/drivers/net/ethernet/qualcomm/emac/emac-mac.c @@ -1449,6 +1449,7 @@ int emac_mac_tx_buf_send(struct emac_adapter *adpt, struct emac_tx_queue *tx_q, { struct emac_tpd tpd; u32 prod_idx; + int len; memset(&tpd, 0, sizeof(tpd)); @@ -1468,9 +1469,10 @@ int emac_mac_tx_buf_send(struct emac_adapter *adpt, struct emac_tx_queue *tx_q, if (skb_network_offset(skb) != ETH_HLEN) TPD_TYP_SET(&tpd, 1); + len = skb->len; emac_tx_fill_tpd(adpt, tx_q, skb, &tpd); - netdev_sent_queue(adpt->netdev, skb->len); + netdev_sent_queue(adpt->netdev, len); /* Make sure the are enough free descriptors to hold one * maximum-sized SKB. We need one desc for each fragment, diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c b/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c index 826626e870d5c..0f56f8e336917 100644 --- a/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c +++ b/drivers/net/ethernet/stmicro/stmmac/dwmac-ipq806x.c @@ -351,6 +351,8 @@ static int ipq806x_gmac_probe(struct platform_device *pdev) plat_dat->bsp_priv = gmac; plat_dat->fix_mac_speed = ipq806x_gmac_fix_mac_speed; plat_dat->multicast_filter_bins = 0; + plat_dat->tx_fifo_size = 8192; + plat_dat->rx_fifo_size = 8192; err = stmmac_dvr_probe(&pdev->dev, plat_dat, &stmmac_res); if (err) diff --git a/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c b/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c index 8c3780d1105fe..232efe17ac2c6 100644 --- a/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c +++ b/drivers/net/ethernet/stmicro/stmmac/dwmac4_dma.c @@ -214,7 +214,7 @@ static void dwmac4_dma_rx_chan_op_mode(void __iomem *ioaddr, int mode, u32 channel, int fifosz, u8 qmode) { unsigned int rqs = fifosz / 256 - 1; - u32 mtl_rx_op, mtl_rx_int; + u32 mtl_rx_op; mtl_rx_op = readl(ioaddr + MTL_CHAN_RX_OP_MODE(channel)); @@ -285,11 +285,6 @@ static void dwmac4_dma_rx_chan_op_mode(void __iomem *ioaddr, int mode, } writel(mtl_rx_op, ioaddr + MTL_CHAN_RX_OP_MODE(channel)); - - /* Enable MTL RX overflow */ - mtl_rx_int = readl(ioaddr + MTL_CHAN_INT_CTRL(channel)); - writel(mtl_rx_int | MTL_RX_OVERFLOW_INT_EN, - ioaddr + MTL_CHAN_INT_CTRL(channel)); } static void dwmac4_dma_tx_chan_op_mode(void __iomem *ioaddr, int mode, diff --git a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c index a1443d7197e87..af59761ddfa07 100644 --- a/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +++ b/drivers/net/ethernet/stmicro/stmmac/stmmac_main.c @@ -3706,7 +3706,6 @@ static irqreturn_t stmmac_interrupt(int irq, void *dev_id) /* To handle GMAC own interrupts */ if ((priv->plat->has_gmac) || xmac) { int status = stmmac_host_irq_status(priv, priv->hw, &priv->xstats); - int mtl_status; if (unlikely(status)) { /* For LPI we need to save the tx status */ @@ -3717,17 +3716,8 @@ static irqreturn_t stmmac_interrupt(int irq, void *dev_id) } for (queue = 0; queue < queues_count; queue++) { - struct stmmac_rx_queue *rx_q = &priv->rx_queue[queue]; - - mtl_status = stmmac_host_mtl_irq_status(priv, priv->hw, - queue); - if (mtl_status != -EINVAL) - status |= mtl_status; - - if (status & CORE_IRQ_MTL_RX_OVERFLOW) - stmmac_set_rx_tail_ptr(priv, priv->ioaddr, - rx_q->rx_tail_addr, - queue); + status = stmmac_host_mtl_irq_status(priv, priv->hw, + queue); } /* PCS link status */ diff --git a/drivers/net/ethernet/ti/davinci_emac.c b/drivers/net/ethernet/ti/davinci_emac.c index f270beebb4289..9bb84d83afc15 100644 --- a/drivers/net/ethernet/ti/davinci_emac.c +++ b/drivers/net/ethernet/ti/davinci_emac.c @@ -183,11 +183,11 @@ static const char emac_version_string[] = "TI DaVinci EMAC Linux v6.1"; /* EMAC mac_status register */ #define EMAC_MACSTATUS_TXERRCODE_MASK (0xF00000) #define EMAC_MACSTATUS_TXERRCODE_SHIFT (20) -#define EMAC_MACSTATUS_TXERRCH_MASK (0x7) +#define EMAC_MACSTATUS_TXERRCH_MASK (0x70000) #define EMAC_MACSTATUS_TXERRCH_SHIFT (16) #define EMAC_MACSTATUS_RXERRCODE_MASK (0xF000) #define EMAC_MACSTATUS_RXERRCODE_SHIFT (12) -#define EMAC_MACSTATUS_RXERRCH_MASK (0x7) +#define EMAC_MACSTATUS_RXERRCH_MASK (0x700) #define EMAC_MACSTATUS_RXERRCH_SHIFT (8) /* EMAC RX register masks */ diff --git a/drivers/net/fddi/Kconfig b/drivers/net/fddi/Kconfig index 3a424c864f4db..ecebeeb9b2a02 100644 --- a/drivers/net/fddi/Kconfig +++ b/drivers/net/fddi/Kconfig @@ -28,17 +28,20 @@ config DEFXX config DEFXX_MMIO bool - prompt "Use MMIO instead of PIO" if PCI || EISA + prompt "Use MMIO instead of IOP" if PCI || EISA depends on DEFXX - default n if PCI || EISA + default n if EISA default y ---help--- This instructs the driver to use EISA or PCI memory-mapped I/O - (MMIO) as appropriate instead of programmed I/O ports (PIO). + (MMIO) as appropriate instead of programmed I/O ports (IOP). Enabling this gives an improvement in processing time in parts - of the driver, but it may cause problems with EISA (DEFEA) - adapters. TURBOchannel does not have the concept of I/O ports, - so MMIO is always used for these (DEFTA) adapters. + of the driver, but it requires a memory window to be configured + for EISA (DEFEA) adapters that may not always be available. + Conversely some PCIe host bridges do not support IOP, so MMIO + may be required to access PCI (DEFPA) adapters on downstream PCI + buses with some systems. TURBOchannel does not have the concept + of I/O ports, so MMIO is always used for these (DEFTA) adapters. If unsure, say N. diff --git a/drivers/net/fddi/defxx.c b/drivers/net/fddi/defxx.c index 61fceee73c1ba..3b48c890540ac 100644 --- a/drivers/net/fddi/defxx.c +++ b/drivers/net/fddi/defxx.c @@ -495,6 +495,25 @@ static const struct net_device_ops dfx_netdev_ops = { .ndo_set_mac_address = dfx_ctl_set_mac_address, }; +static void dfx_register_res_alloc_err(const char *print_name, bool mmio, + bool eisa) +{ + pr_err("%s: Cannot use %s, no address set, aborting\n", + print_name, mmio ? "MMIO" : "I/O"); + pr_err("%s: Recompile driver with \"CONFIG_DEFXX_MMIO=%c\"\n", + print_name, mmio ? 'n' : 'y'); + if (eisa && mmio) + pr_err("%s: Or run ECU and set adapter's MMIO location\n", + print_name); +} + +static void dfx_register_res_err(const char *print_name, bool mmio, + unsigned long start, unsigned long len) +{ + pr_err("%s: Cannot reserve %s resource 0x%lx @ 0x%lx, aborting\n", + print_name, mmio ? "MMIO" : "I/O", len, start); +} + /* * ================ * = dfx_register = @@ -568,15 +587,12 @@ static int dfx_register(struct device *bdev) dev_set_drvdata(bdev, dev); dfx_get_bars(bdev, bar_start, bar_len); - if (dfx_bus_eisa && dfx_use_mmio && bar_start[0] == 0) { - pr_err("%s: Cannot use MMIO, no address set, aborting\n", - print_name); - pr_err("%s: Run ECU and set adapter's MMIO location\n", - print_name); - pr_err("%s: Or recompile driver with \"CONFIG_DEFXX_MMIO=n\"" - "\n", print_name); + if (bar_len[0] == 0 || + (dfx_bus_eisa && dfx_use_mmio && bar_start[0] == 0)) { + dfx_register_res_alloc_err(print_name, dfx_use_mmio, + dfx_bus_eisa); err = -ENXIO; - goto err_out; + goto err_out_disable; } if (dfx_use_mmio) @@ -585,18 +601,16 @@ static int dfx_register(struct device *bdev) else region = request_region(bar_start[0], bar_len[0], print_name); if (!region) { - pr_err("%s: Cannot reserve %s resource 0x%lx @ 0x%lx, " - "aborting\n", dfx_use_mmio ? "MMIO" : "I/O", print_name, - (long)bar_len[0], (long)bar_start[0]); + dfx_register_res_err(print_name, dfx_use_mmio, + bar_start[0], bar_len[0]); err = -EBUSY; goto err_out_disable; } if (bar_start[1] != 0) { region = request_region(bar_start[1], bar_len[1], print_name); if (!region) { - pr_err("%s: Cannot reserve I/O resource " - "0x%lx @ 0x%lx, aborting\n", print_name, - (long)bar_len[1], (long)bar_start[1]); + dfx_register_res_err(print_name, 0, + bar_start[1], bar_len[1]); err = -EBUSY; goto err_out_csr_region; } @@ -604,9 +618,8 @@ static int dfx_register(struct device *bdev) if (bar_start[2] != 0) { region = request_region(bar_start[2], bar_len[2], print_name); if (!region) { - pr_err("%s: Cannot reserve I/O resource " - "0x%lx @ 0x%lx, aborting\n", print_name, - (long)bar_len[2], (long)bar_start[2]); + dfx_register_res_err(print_name, 0, + bar_start[2], bar_len[2]); err = -EBUSY; goto err_out_bh_region; } diff --git a/drivers/net/geneve.c b/drivers/net/geneve.c index ce6fecf421f86..8c458c8f57a3b 100644 --- a/drivers/net/geneve.c +++ b/drivers/net/geneve.c @@ -839,7 +839,7 @@ static int geneve_xmit_skb(struct sk_buff *skb, struct net_device *dev, __be16 df; int err; - if (!pskb_network_may_pull(skb, sizeof(struct iphdr))) + if (!pskb_inet_may_pull(skb)) return -EINVAL; sport = udp_flow_src_port(geneve->net, skb, 1, USHRT_MAX, true); @@ -885,7 +885,7 @@ static int geneve6_xmit_skb(struct sk_buff *skb, struct net_device *dev, __be16 sport; int err; - if (!pskb_network_may_pull(skb, sizeof(struct ipv6hdr))) + if (!pskb_inet_may_pull(skb)) return -EINVAL; sport = udp_flow_src_port(geneve->net, skb, 1, USHRT_MAX, true); diff --git a/drivers/net/wan/lapbether.c b/drivers/net/wan/lapbether.c index fad5fc8b9edb9..3ec922bed2d84 100644 --- a/drivers/net/wan/lapbether.c +++ b/drivers/net/wan/lapbether.c @@ -56,6 +56,8 @@ struct lapbethdev { struct list_head node; struct net_device *ethdev; /* link to ethernet device */ struct net_device *axdev; /* lapbeth device (lapb#) */ + bool up; + spinlock_t up_lock; /* Protects "up" */ }; static LIST_HEAD(lapbeth_devices); @@ -103,8 +105,9 @@ static int lapbeth_rcv(struct sk_buff *skb, struct net_device *dev, struct packe rcu_read_lock(); lapbeth = lapbeth_get_x25_dev(dev); if (!lapbeth) - goto drop_unlock; - if (!netif_running(lapbeth->axdev)) + goto drop_unlock_rcu; + spin_lock_bh(&lapbeth->up_lock); + if (!lapbeth->up) goto drop_unlock; len = skb->data[0] + skb->data[1] * 256; @@ -119,11 +122,14 @@ static int lapbeth_rcv(struct sk_buff *skb, struct net_device *dev, struct packe goto drop_unlock; } out: + spin_unlock_bh(&lapbeth->up_lock); rcu_read_unlock(); return 0; drop_unlock: kfree_skb(skb); goto out; +drop_unlock_rcu: + rcu_read_unlock(); drop: kfree_skb(skb); return 0; @@ -151,13 +157,11 @@ static int lapbeth_data_indication(struct net_device *dev, struct sk_buff *skb) static netdev_tx_t lapbeth_xmit(struct sk_buff *skb, struct net_device *dev) { + struct lapbethdev *lapbeth = netdev_priv(dev); int err; - /* - * Just to be *really* sure not to send anything if the interface - * is down, the ethernet device may have gone. - */ - if (!netif_running(dev)) + spin_lock_bh(&lapbeth->up_lock); + if (!lapbeth->up) goto drop; /* There should be a pseudo header of 1 byte added by upper layers. @@ -188,6 +192,7 @@ static netdev_tx_t lapbeth_xmit(struct sk_buff *skb, goto drop; } out: + spin_unlock_bh(&lapbeth->up_lock); return NETDEV_TX_OK; drop: kfree_skb(skb); @@ -279,6 +284,7 @@ static const struct lapb_register_struct lapbeth_callbacks = { */ static int lapbeth_open(struct net_device *dev) { + struct lapbethdev *lapbeth = netdev_priv(dev); int err; if ((err = lapb_register(dev, &lapbeth_callbacks)) != LAPB_OK) { @@ -286,13 +292,22 @@ static int lapbeth_open(struct net_device *dev) return -ENODEV; } + spin_lock_bh(&lapbeth->up_lock); + lapbeth->up = true; + spin_unlock_bh(&lapbeth->up_lock); + return 0; } static int lapbeth_close(struct net_device *dev) { + struct lapbethdev *lapbeth = netdev_priv(dev); int err; + spin_lock_bh(&lapbeth->up_lock); + lapbeth->up = false; + spin_unlock_bh(&lapbeth->up_lock); + if ((err = lapb_unregister(dev)) != LAPB_OK) pr_err("lapb_unregister error: %d\n", err); @@ -350,6 +365,9 @@ static int lapbeth_new_device(struct net_device *dev) dev_hold(dev); lapbeth->ethdev = dev; + lapbeth->up = false; + spin_lock_init(&lapbeth->up_lock); + rc = -EIO; if (register_netdevice(ndev)) goto fail; diff --git a/drivers/net/wimax/i2400m/op-rfkill.c b/drivers/net/wimax/i2400m/op-rfkill.c index dc6fe93ce71f6..e8473047b2d1e 100644 --- a/drivers/net/wimax/i2400m/op-rfkill.c +++ b/drivers/net/wimax/i2400m/op-rfkill.c @@ -101,7 +101,7 @@ int i2400m_op_rfkill_sw_toggle(struct wimax_dev *wimax_dev, if (cmd == NULL) goto error_alloc; cmd->hdr.type = cpu_to_le16(I2400M_MT_CMD_RF_CONTROL); - cmd->hdr.length = sizeof(cmd->sw_rf); + cmd->hdr.length = cpu_to_le16(sizeof(cmd->sw_rf)); cmd->hdr.version = cpu_to_le16(I2400M_L3L4_VERSION); cmd->sw_rf.hdr.type = cpu_to_le16(I2400M_TLV_RF_OPERATION); cmd->sw_rf.hdr.length = cpu_to_le16(sizeof(cmd->sw_rf.status)); diff --git a/drivers/net/wireless/ath/ath10k/wmi-tlv.c b/drivers/net/wireless/ath/ath10k/wmi-tlv.c index 04dc5714aa725..243887fdb343e 100644 --- a/drivers/net/wireless/ath/ath10k/wmi-tlv.c +++ b/drivers/net/wireless/ath/ath10k/wmi-tlv.c @@ -465,6 +465,9 @@ static void ath10k_wmi_event_tdls_peer(struct ath10k *ar, struct sk_buff *skb) GFP_ATOMIC ); break; + default: + kfree(tb); + return; } exit: diff --git a/drivers/net/wireless/ath/ath9k/htc_drv_init.c b/drivers/net/wireless/ath/ath9k/htc_drv_init.c index 27d9fe6799f58..cb136d9d46214 100644 --- a/drivers/net/wireless/ath/ath9k/htc_drv_init.c +++ b/drivers/net/wireless/ath/ath9k/htc_drv_init.c @@ -246,7 +246,7 @@ static unsigned int ath9k_regread(void *hw_priv, u32 reg_offset) if (unlikely(r)) { ath_dbg(common, WMI, "REGISTER READ FAILED: (0x%04x, %d)\n", reg_offset, r); - return -EIO; + return -1; } return be32_to_cpu(val); diff --git a/drivers/net/wireless/ath/ath9k/hw.c b/drivers/net/wireless/ath/ath9k/hw.c index b4f7ee423d407..9f438d8e59f2f 100644 --- a/drivers/net/wireless/ath/ath9k/hw.c +++ b/drivers/net/wireless/ath/ath9k/hw.c @@ -287,7 +287,7 @@ static bool ath9k_hw_read_revisions(struct ath_hw *ah) srev = REG_READ(ah, AR_SREV); - if (srev == -EIO) { + if (srev == -1) { ath_err(ath9k_hw_common(ah), "Failed to read SREV register"); return false; diff --git a/drivers/net/wireless/intel/ipw2x00/libipw_wx.c b/drivers/net/wireless/intel/ipw2x00/libipw_wx.c index d32d39fa26862..c129291d3a173 100644 --- a/drivers/net/wireless/intel/ipw2x00/libipw_wx.c +++ b/drivers/net/wireless/intel/ipw2x00/libipw_wx.c @@ -647,8 +647,10 @@ int libipw_wx_set_encodeext(struct libipw_device *ieee, } if (ext->alg != IW_ENCODE_ALG_NONE) { - memcpy(sec.keys[idx], ext->key, ext->key_len); - sec.key_sizes[idx] = ext->key_len; + int key_len = clamp_val(ext->key_len, 0, SCM_KEY_LEN); + + memcpy(sec.keys[idx], ext->key, key_len); + sec.key_sizes[idx] = key_len; sec.flags |= (1 << idx); if (ext->alg == IW_ENCODE_ALG_WEP) { sec.encode_alg[idx] = SEC_ALG_WEP; diff --git a/drivers/net/wireless/marvell/mwl8k.c b/drivers/net/wireless/marvell/mwl8k.c index ffc565ac21924..6769b0c5a5cde 100644 --- a/drivers/net/wireless/marvell/mwl8k.c +++ b/drivers/net/wireless/marvell/mwl8k.c @@ -1469,6 +1469,7 @@ static int mwl8k_txq_init(struct ieee80211_hw *hw, int index) txq->skb = kcalloc(MWL8K_TX_DESCS, sizeof(*txq->skb), GFP_KERNEL); if (txq->skb == NULL) { pci_free_consistent(priv->pdev, size, txq->txd, txq->txd_dma); + txq->txd = NULL; return -ENOMEM; } diff --git a/drivers/net/wireless/mediatek/mt7601u/eeprom.c b/drivers/net/wireless/mediatek/mt7601u/eeprom.c index 76117b4028805..6ab1035e4a121 100644 --- a/drivers/net/wireless/mediatek/mt7601u/eeprom.c +++ b/drivers/net/wireless/mediatek/mt7601u/eeprom.c @@ -107,7 +107,7 @@ mt7601u_has_tssi(struct mt7601u_dev *dev, u8 *eeprom) { u16 nic_conf1 = get_unaligned_le16(eeprom + MT_EE_NIC_CONF_1); - return ~nic_conf1 && (nic_conf1 & MT_EE_NIC_CONF_1_TX_ALC_EN); + return (u16)~nic_conf1 && (nic_conf1 & MT_EE_NIC_CONF_1_TX_ALC_EN); } static void diff --git a/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/table.c b/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/table.c index f87f9d03b9fa2..ac44fd5d05977 100644 --- a/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/table.c +++ b/drivers/net/wireless/realtek/rtlwifi/rtl8821ae/table.c @@ -272,7 +272,7 @@ u32 RTL8821AE_PHY_REG_ARRAY[] = { 0x824, 0x00030FE0, 0x828, 0x00000000, 0x82C, 0x002081DD, - 0x830, 0x2AAA8E24, + 0x830, 0x2AAAEEC8, 0x834, 0x0037A706, 0x838, 0x06489B44, 0x83C, 0x0000095B, @@ -347,10 +347,10 @@ u32 RTL8821AE_PHY_REG_ARRAY[] = { 0x9D8, 0x00000000, 0x9DC, 0x00000000, 0x9E0, 0x00005D00, - 0x9E4, 0x00000002, + 0x9E4, 0x00000003, 0x9E8, 0x00000001, 0xA00, 0x00D047C8, - 0xA04, 0x01FF000C, + 0xA04, 0x01FF800C, 0xA08, 0x8C8A8300, 0xA0C, 0x2E68000F, 0xA10, 0x9500BB78, @@ -1343,7 +1343,11 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x083, 0x00021800, 0x084, 0x00028000, 0x085, 0x00048000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, + 0x086, 0x0009483A, + 0xA0000000, 0x00000000, 0x086, 0x00094838, + 0xB0000000, 0x00000000, 0x087, 0x00044980, 0x088, 0x00048000, 0x089, 0x0000D480, @@ -1432,36 +1436,32 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x03C, 0x000CA000, 0x0EF, 0x00000000, 0x0EF, 0x00001100, - 0xFF0F0104, 0xABCD, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0004ADF3, 0x034, 0x00049DF0, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0004ADF3, 0x034, 0x00049DF0, - 0xFF0F0404, 0xCDEF, - 0x034, 0x0004ADF3, - 0x034, 0x00049DF0, - 0xFF0F0200, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0004ADF5, 0x034, 0x00049DF2, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0004A0F3, + 0x034, 0x000490B1, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0004A0F3, 0x034, 0x000490B1, - 0xCDCDCDCD, 0xCDCD, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0004ADF5, + 0x034, 0x00049DF2, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0004ADF3, + 0x034, 0x00049DF0, + 0xA0000000, 0x00000000, 0x034, 0x0004ADF7, 0x034, 0x00049DF3, - 0xFF0F0104, 0xDEAD, - 0xFF0F0104, 0xABCD, - 0x034, 0x00048DED, - 0x034, 0x00047DEA, - 0x034, 0x00046DE7, - 0x034, 0x00045CE9, - 0x034, 0x00044CE6, - 0x034, 0x000438C6, - 0x034, 0x00042886, - 0x034, 0x00041486, - 0x034, 0x00040447, - 0xFF0F0204, 0xCDEF, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00048DED, 0x034, 0x00047DEA, 0x034, 0x00046DE7, @@ -1471,7 +1471,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00042886, 0x034, 0x00041486, 0x034, 0x00040447, - 0xFF0F0404, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00048DED, 0x034, 0x00047DEA, 0x034, 0x00046DE7, @@ -1481,7 +1481,17 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00042886, 0x034, 0x00041486, 0x034, 0x00040447, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x000480AE, + 0x034, 0x000470AB, + 0x034, 0x0004608B, + 0x034, 0x00045069, + 0x034, 0x00044048, + 0x034, 0x00043045, + 0x034, 0x00042026, + 0x034, 0x00041023, + 0x034, 0x00040002, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x000480AE, 0x034, 0x000470AB, 0x034, 0x0004608B, @@ -1491,7 +1501,17 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00042026, 0x034, 0x00041023, 0x034, 0x00040002, - 0xCDCDCDCD, 0xCDCD, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x00048DED, + 0x034, 0x00047DEA, + 0x034, 0x00046DE7, + 0x034, 0x00045CE9, + 0x034, 0x00044CE6, + 0x034, 0x000438C6, + 0x034, 0x00042886, + 0x034, 0x00041486, + 0x034, 0x00040447, + 0xA0000000, 0x00000000, 0x034, 0x00048DEF, 0x034, 0x00047DEC, 0x034, 0x00046DE9, @@ -1501,38 +1521,36 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x0004248A, 0x034, 0x0004108D, 0x034, 0x0004008A, - 0xFF0F0104, 0xDEAD, - 0xFF0F0200, 0xABCD, + 0xB0000000, 0x00000000, + 0x80000210, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0002ADF4, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0002A0F3, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0002A0F3, - 0xCDCDCDCD, 0xCDCD, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0002ADF4, + 0xA0000000, 0x00000000, 0x034, 0x0002ADF7, - 0xFF0F0200, 0xDEAD, - 0xFF0F0104, 0xABCD, - 0x034, 0x00029DF4, - 0xFF0F0204, 0xCDEF, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00029DF4, - 0xFF0F0404, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00029DF4, - 0xFF0F0200, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00029DF1, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x000290F0, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x000290F0, - 0xCDCDCDCD, 0xCDCD, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x00029DF1, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x00029DF4, + 0xA0000000, 0x00000000, 0x034, 0x00029DF2, - 0xFF0F0104, 0xDEAD, - 0xFF0F0104, 0xABCD, - 0x034, 0x00028DF1, - 0x034, 0x00027DEE, - 0x034, 0x00026DEB, - 0x034, 0x00025CEC, - 0x034, 0x00024CE9, - 0x034, 0x000238CA, - 0x034, 0x00022889, - 0x034, 0x00021489, - 0x034, 0x0002044A, - 0xFF0F0204, 0xCDEF, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00028DF1, 0x034, 0x00027DEE, 0x034, 0x00026DEB, @@ -1542,7 +1560,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00022889, 0x034, 0x00021489, 0x034, 0x0002044A, - 0xFF0F0404, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00028DF1, 0x034, 0x00027DEE, 0x034, 0x00026DEB, @@ -1552,7 +1570,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00022889, 0x034, 0x00021489, 0x034, 0x0002044A, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x000280AF, 0x034, 0x000270AC, 0x034, 0x0002608B, @@ -1562,7 +1580,27 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00022026, 0x034, 0x00021023, 0x034, 0x00020002, - 0xCDCDCDCD, 0xCDCD, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x000280AF, + 0x034, 0x000270AC, + 0x034, 0x0002608B, + 0x034, 0x00025069, + 0x034, 0x00024048, + 0x034, 0x00023045, + 0x034, 0x00022026, + 0x034, 0x00021023, + 0x034, 0x00020002, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x00028DF1, + 0x034, 0x00027DEE, + 0x034, 0x00026DEB, + 0x034, 0x00025CEC, + 0x034, 0x00024CE9, + 0x034, 0x000238CA, + 0x034, 0x00022889, + 0x034, 0x00021489, + 0x034, 0x0002044A, + 0xA0000000, 0x00000000, 0x034, 0x00028DEE, 0x034, 0x00027DEB, 0x034, 0x00026CCD, @@ -1572,27 +1610,24 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00022849, 0x034, 0x00021449, 0x034, 0x0002004D, - 0xFF0F0104, 0xDEAD, - 0xFF0F02C0, 0xABCD, + 0xB0000000, 0x00000000, + 0x8000020c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0000A0D7, + 0x034, 0x000090D3, + 0x034, 0x000080B1, + 0x034, 0x000070AE, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0000A0D7, 0x034, 0x000090D3, 0x034, 0x000080B1, 0x034, 0x000070AE, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x034, 0x0000ADF7, 0x034, 0x00009DF4, 0x034, 0x00008DF1, 0x034, 0x00007DEE, - 0xFF0F02C0, 0xDEAD, - 0xFF0F0104, 0xABCD, - 0x034, 0x00006DEB, - 0x034, 0x00005CEC, - 0x034, 0x00004CE9, - 0x034, 0x000038CA, - 0x034, 0x00002889, - 0x034, 0x00001489, - 0x034, 0x0000044A, - 0xFF0F0204, 0xCDEF, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00006DEB, 0x034, 0x00005CEC, 0x034, 0x00004CE9, @@ -1600,7 +1635,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00002889, 0x034, 0x00001489, 0x034, 0x0000044A, - 0xFF0F0404, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x00006DEB, 0x034, 0x00005CEC, 0x034, 0x00004CE9, @@ -1608,7 +1643,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00002889, 0x034, 0x00001489, 0x034, 0x0000044A, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, 0x034, 0x0000608D, 0x034, 0x0000506B, 0x034, 0x0000404A, @@ -1616,7 +1651,23 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00002044, 0x034, 0x00001025, 0x034, 0x00000004, - 0xCDCDCDCD, 0xCDCD, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x0000608D, + 0x034, 0x0000506B, + 0x034, 0x0000404A, + 0x034, 0x00003047, + 0x034, 0x00002044, + 0x034, 0x00001025, + 0x034, 0x00000004, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x034, 0x00006DEB, + 0x034, 0x00005CEC, + 0x034, 0x00004CE9, + 0x034, 0x000038CA, + 0x034, 0x00002889, + 0x034, 0x00001489, + 0x034, 0x0000044A, + 0xA0000000, 0x00000000, 0x034, 0x00006DCD, 0x034, 0x00005CCD, 0x034, 0x00004CCA, @@ -1624,11 +1675,11 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x034, 0x00002888, 0x034, 0x00001488, 0x034, 0x00000486, - 0xFF0F0104, 0xDEAD, + 0xB0000000, 0x00000000, 0x0EF, 0x00000000, 0x018, 0x0001712A, 0x0EF, 0x00000040, - 0xFF0F0104, 0xABCD, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x035, 0x00000187, 0x035, 0x00008187, 0x035, 0x00010187, @@ -1638,7 +1689,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x035, 0x00040188, 0x035, 0x00048188, 0x035, 0x00050188, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x035, 0x00000187, 0x035, 0x00008187, 0x035, 0x00010187, @@ -1648,7 +1699,37 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x035, 0x00040188, 0x035, 0x00048188, 0x035, 0x00050188, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, + 0x035, 0x00000128, + 0x035, 0x00008128, + 0x035, 0x00010128, + 0x035, 0x000201C8, + 0x035, 0x000281C8, + 0x035, 0x000301C8, + 0x035, 0x000401C8, + 0x035, 0x000481C8, + 0x035, 0x000501C8, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x035, 0x00000145, + 0x035, 0x00008145, + 0x035, 0x00010145, + 0x035, 0x00020196, + 0x035, 0x00028196, + 0x035, 0x00030196, + 0x035, 0x000401C7, + 0x035, 0x000481C7, + 0x035, 0x000501C7, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x035, 0x00000128, + 0x035, 0x00008128, + 0x035, 0x00010128, + 0x035, 0x000201C8, + 0x035, 0x000281C8, + 0x035, 0x000301C8, + 0x035, 0x000401C8, + 0x035, 0x000481C8, + 0x035, 0x000501C8, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x035, 0x00000187, 0x035, 0x00008187, 0x035, 0x00010187, @@ -1658,7 +1739,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x035, 0x00040188, 0x035, 0x00048188, 0x035, 0x00050188, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x035, 0x00000145, 0x035, 0x00008145, 0x035, 0x00010145, @@ -1668,11 +1749,11 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x035, 0x000401C7, 0x035, 0x000481C7, 0x035, 0x000501C7, - 0xFF0F0104, 0xDEAD, + 0xB0000000, 0x00000000, 0x0EF, 0x00000000, 0x018, 0x0001712A, 0x0EF, 0x00000010, - 0xFF0F0104, 0xABCD, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x036, 0x00085733, 0x036, 0x0008D733, 0x036, 0x00095733, @@ -1685,7 +1766,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x036, 0x000CE4B4, 0x036, 0x000D64B4, 0x036, 0x000DE4B4, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x036, 0x00085733, 0x036, 0x0008D733, 0x036, 0x00095733, @@ -1698,7 +1779,46 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x036, 0x000CE4B4, 0x036, 0x000D64B4, 0x036, 0x000DE4B4, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, + 0x036, 0x000063B5, + 0x036, 0x0000E3B5, + 0x036, 0x000163B5, + 0x036, 0x0001E3B5, + 0x036, 0x000263B5, + 0x036, 0x0002E3B5, + 0x036, 0x000363B5, + 0x036, 0x0003E3B5, + 0x036, 0x000463B5, + 0x036, 0x0004E3B5, + 0x036, 0x000563B5, + 0x036, 0x0005E3B5, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x036, 0x000056B3, + 0x036, 0x0000D6B3, + 0x036, 0x000156B3, + 0x036, 0x0001D6B3, + 0x036, 0x00026634, + 0x036, 0x0002E634, + 0x036, 0x00036634, + 0x036, 0x0003E634, + 0x036, 0x000467B4, + 0x036, 0x0004E7B4, + 0x036, 0x000567B4, + 0x036, 0x0005E7B4, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x036, 0x000063B5, + 0x036, 0x0000E3B5, + 0x036, 0x000163B5, + 0x036, 0x0001E3B5, + 0x036, 0x000263B5, + 0x036, 0x0002E3B5, + 0x036, 0x000363B5, + 0x036, 0x0003E3B5, + 0x036, 0x000463B5, + 0x036, 0x0004E3B5, + 0x036, 0x000563B5, + 0x036, 0x0005E3B5, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x036, 0x00085733, 0x036, 0x0008D733, 0x036, 0x00095733, @@ -1711,7 +1831,7 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x036, 0x000CE4B4, 0x036, 0x000D64B4, 0x036, 0x000DE4B4, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x036, 0x000056B3, 0x036, 0x0000D6B3, 0x036, 0x000156B3, @@ -1724,103 +1844,162 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x036, 0x0004E7B4, 0x036, 0x000567B4, 0x036, 0x0005E7B4, - 0xFF0F0104, 0xDEAD, + 0xB0000000, 0x00000000, 0x0EF, 0x00000000, 0x0EF, 0x00000008, - 0xFF0F0104, 0xABCD, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x000001C8, 0x03C, 0x00000492, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x000001C8, 0x03C, 0x00000492, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, + 0x03C, 0x000001B6, + 0x03C, 0x00000492, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x03C, 0x0000022A, + 0x03C, 0x00000594, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x03C, 0x000001B6, + 0x03C, 0x00000492, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x000001C8, 0x03C, 0x00000492, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x03C, 0x0000022A, 0x03C, 0x00000594, - 0xFF0F0104, 0xDEAD, - 0xFF0F0104, 0xABCD, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x00000800, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x00000800, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x00000800, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, 0x03C, 0x00000820, - 0xCDCDCDCD, 0xCDCD, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x03C, 0x00000820, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x03C, 0x00000800, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x03C, 0x00000800, + 0xA0000000, 0x00000000, 0x03C, 0x00000900, - 0xFF0F0104, 0xDEAD, + 0xB0000000, 0x00000000, 0x0EF, 0x00000000, 0x018, 0x0001712A, 0x0EF, 0x00000002, - 0xFF0F0104, 0xABCD, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x008, 0x0004E400, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x008, 0x0004E400, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, + 0x008, 0x00002000, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, + 0x008, 0x00002000, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x008, 0x00002000, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x008, 0x00002000, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x008, 0x0004E400, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x008, 0x00002000, - 0xFF0F0104, 0xDEAD, + 0xB0000000, 0x00000000, 0x0EF, 0x00000000, 0x0DF, 0x000000C0, - 0x01F, 0x00040064, - 0xFF0F0104, 0xABCD, + 0x01F, 0x00000064, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x058, 0x000A7284, 0x059, 0x000600EC, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x058, 0x000A7284, 0x059, 0x000600EC, - 0xFF0F0404, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, + 0x058, 0x00081184, + 0x059, 0x0006016C, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x058, 0x00081184, + 0x059, 0x0006016C, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x058, 0x00081184, + 0x059, 0x0006016C, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x058, 0x000A7284, 0x059, 0x000600EC, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x058, 0x00081184, 0x059, 0x0006016C, - 0xFF0F0104, 0xDEAD, - 0xFF0F0104, 0xABCD, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x061, 0x000E8D73, 0x062, 0x00093FC5, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x061, 0x000E8D73, 0x062, 0x00093FC5, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, + 0x061, 0x000EFD83, + 0x062, 0x00093FCC, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x061, 0x000EAD53, + 0x062, 0x00093BC4, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x061, 0x000EFD83, + 0x062, 0x00093FCC, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x061, 0x000E8D73, 0x062, 0x00093FC5, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x061, 0x000EAD53, 0x062, 0x00093BC4, - 0xFF0F0104, 0xDEAD, - 0xFF0F0104, 0xABCD, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, 0x063, 0x000110E9, - 0xFF0F0204, 0xCDEF, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, 0x063, 0x000110E9, - 0xFF0F0404, 0xCDEF, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, + 0x063, 0x000110EB, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, 0x063, 0x000110E9, - 0xFF0F0200, 0xCDEF, - 0x063, 0x000710E9, - 0xFF0F02C0, 0xCDEF, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x063, 0x000110E9, - 0xCDCDCDCD, 0xCDCD, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x063, 0x000110EB, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, + 0x063, 0x000110E9, + 0xA0000000, 0x00000000, 0x063, 0x000714E9, - 0xFF0F0104, 0xDEAD, - 0xFF0F0104, 0xABCD, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, + 0x064, 0x0001C27C, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, + 0x064, 0x0001C27C, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, 0x064, 0x0001C27C, - 0xFF0F0204, 0xCDEF, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x064, 0x0001C67C, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, 0x064, 0x0001C27C, - 0xFF0F0404, 0xCDEF, + 0x90000410, 0x00000000, 0x40000000, 0x00000000, 0x064, 0x0001C27C, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x064, 0x0001C67C, - 0xFF0F0104, 0xDEAD, - 0xFF0F0200, 0xABCD, + 0xB0000000, 0x00000000, + 0x80000111, 0x00000000, 0x40000000, 0x00000000, + 0x065, 0x00091016, + 0x90000110, 0x00000000, 0x40000000, 0x00000000, + 0x065, 0x00091016, + 0x90000210, 0x00000000, 0x40000000, 0x00000000, 0x065, 0x00093016, - 0xFF0F02C0, 0xCDEF, + 0x9000020c, 0x00000000, 0x40000000, 0x00000000, 0x065, 0x00093015, - 0xCDCDCDCD, 0xCDCD, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, + 0x065, 0x00093015, + 0x90000200, 0x00000000, 0x40000000, 0x00000000, + 0x065, 0x00093016, + 0xA0000000, 0x00000000, 0x065, 0x00091016, - 0xFF0F0200, 0xDEAD, + 0xB0000000, 0x00000000, 0x018, 0x00000006, 0x0EF, 0x00002000, 0x03B, 0x0003824B, @@ -1918,9 +2097,10 @@ u32 RTL8821AE_RADIOA_ARRAY[] = { 0x0B4, 0x0001214C, 0x0B7, 0x0003000C, 0x01C, 0x000539D2, + 0x0C4, 0x000AFE00, 0x018, 0x0001F12A, - 0x0FE, 0x00000000, - 0x0FE, 0x00000000, + 0xFFE, 0x00000000, + 0xFFE, 0x00000000, 0x018, 0x0001712A, }; @@ -2040,6 +2220,7 @@ u32 RTL8812AE_MAC_REG_ARRAY[] = { u32 RTL8812AE_MAC_1T_ARRAYLEN = ARRAY_SIZE(RTL8812AE_MAC_REG_ARRAY); u32 RTL8821AE_MAC_REG_ARRAY[] = { + 0x421, 0x0000000F, 0x428, 0x0000000A, 0x429, 0x00000010, 0x430, 0x00000000, @@ -2508,7 +2689,7 @@ u32 RTL8821AE_AGC_TAB_ARRAY[] = { 0x81C, 0xA6360001, 0x81C, 0xA5380001, 0x81C, 0xA43A0001, - 0x81C, 0xA33C0001, + 0x81C, 0x683C0001, 0x81C, 0x673E0001, 0x81C, 0x66400001, 0x81C, 0x65420001, @@ -2542,7 +2723,66 @@ u32 RTL8821AE_AGC_TAB_ARRAY[] = { 0x81C, 0x017A0001, 0x81C, 0x017C0001, 0x81C, 0x017E0001, - 0xFF0F02C0, 0xABCD, + 0x8000020c, 0x00000000, 0x40000000, 0x00000000, + 0x81C, 0xFB000101, + 0x81C, 0xFA020101, + 0x81C, 0xF9040101, + 0x81C, 0xF8060101, + 0x81C, 0xF7080101, + 0x81C, 0xF60A0101, + 0x81C, 0xF50C0101, + 0x81C, 0xF40E0101, + 0x81C, 0xF3100101, + 0x81C, 0xF2120101, + 0x81C, 0xF1140101, + 0x81C, 0xF0160101, + 0x81C, 0xEF180101, + 0x81C, 0xEE1A0101, + 0x81C, 0xED1C0101, + 0x81C, 0xEC1E0101, + 0x81C, 0xEB200101, + 0x81C, 0xEA220101, + 0x81C, 0xE9240101, + 0x81C, 0xE8260101, + 0x81C, 0xE7280101, + 0x81C, 0xE62A0101, + 0x81C, 0xE52C0101, + 0x81C, 0xE42E0101, + 0x81C, 0xE3300101, + 0x81C, 0xA5320101, + 0x81C, 0xA4340101, + 0x81C, 0xA3360101, + 0x81C, 0x87380101, + 0x81C, 0x863A0101, + 0x81C, 0x853C0101, + 0x81C, 0x843E0101, + 0x81C, 0x69400101, + 0x81C, 0x68420101, + 0x81C, 0x67440101, + 0x81C, 0x66460101, + 0x81C, 0x49480101, + 0x81C, 0x484A0101, + 0x81C, 0x474C0101, + 0x81C, 0x2A4E0101, + 0x81C, 0x29500101, + 0x81C, 0x28520101, + 0x81C, 0x27540101, + 0x81C, 0x26560101, + 0x81C, 0x25580101, + 0x81C, 0x245A0101, + 0x81C, 0x235C0101, + 0x81C, 0x055E0101, + 0x81C, 0x04600101, + 0x81C, 0x03620101, + 0x81C, 0x02640101, + 0x81C, 0x01660101, + 0x81C, 0x01680101, + 0x81C, 0x016A0101, + 0x81C, 0x016C0101, + 0x81C, 0x016E0101, + 0x81C, 0x01700101, + 0x81C, 0x01720101, + 0x9000040c, 0x00000000, 0x40000000, 0x00000000, 0x81C, 0xFB000101, 0x81C, 0xFA020101, 0x81C, 0xF9040101, @@ -2601,7 +2841,7 @@ u32 RTL8821AE_AGC_TAB_ARRAY[] = { 0x81C, 0x016E0101, 0x81C, 0x01700101, 0x81C, 0x01720101, - 0xCDCDCDCD, 0xCDCD, + 0xA0000000, 0x00000000, 0x81C, 0xFF000101, 0x81C, 0xFF020101, 0x81C, 0xFE040101, @@ -2660,7 +2900,7 @@ u32 RTL8821AE_AGC_TAB_ARRAY[] = { 0x81C, 0x046E0101, 0x81C, 0x03700101, 0x81C, 0x02720101, - 0xFF0F02C0, 0xDEAD, + 0xB0000000, 0x00000000, 0x81C, 0x01740101, 0x81C, 0x01760101, 0x81C, 0x01780101, diff --git a/drivers/net/wireless/rsi/rsi_91x_sdio.c b/drivers/net/wireless/rsi/rsi_91x_sdio.c index f76a360cf1e35..609cd07eeafca 100644 --- a/drivers/net/wireless/rsi/rsi_91x_sdio.c +++ b/drivers/net/wireless/rsi/rsi_91x_sdio.c @@ -1400,7 +1400,7 @@ static int rsi_restore(struct device *dev) } static const struct dev_pm_ops rsi_pm_ops = { .suspend = rsi_suspend, - .resume = rsi_resume, + .resume_noirq = rsi_resume, .freeze = rsi_freeze, .thaw = rsi_thaw, .restore = rsi_restore, diff --git a/drivers/net/wireless/wl3501.h b/drivers/net/wireless/wl3501.h index efdce9ae36ea7..a10ee5a680129 100644 --- a/drivers/net/wireless/wl3501.h +++ b/drivers/net/wireless/wl3501.h @@ -379,16 +379,7 @@ struct wl3501_get_confirm { u8 mib_value[100]; }; -struct wl3501_join_req { - u16 next_blk; - u8 sig_id; - u8 reserved; - struct iw_mgmt_data_rset operational_rset; - u16 reserved2; - u16 timeout; - u16 probe_delay; - u8 timestamp[8]; - u8 local_time[8]; +struct wl3501_req { u16 beacon_period; u16 dtim_period; u16 cap_info; @@ -401,6 +392,19 @@ struct wl3501_join_req { struct iw_mgmt_data_rset bss_basic_rset; }; +struct wl3501_join_req { + u16 next_blk; + u8 sig_id; + u8 reserved; + struct iw_mgmt_data_rset operational_rset; + u16 reserved2; + u16 timeout; + u16 probe_delay; + u8 timestamp[8]; + u8 local_time[8]; + struct wl3501_req req; +}; + struct wl3501_join_confirm { u16 next_blk; u8 sig_id; @@ -443,16 +447,7 @@ struct wl3501_scan_confirm { u16 status; char timestamp[8]; char localtime[8]; - u16 beacon_period; - u16 dtim_period; - u16 cap_info; - u8 bss_type; - u8 bssid[ETH_ALEN]; - struct iw_mgmt_essid_pset ssid; - struct iw_mgmt_ds_pset ds_pset; - struct iw_mgmt_cf_pset cf_pset; - struct iw_mgmt_ibss_pset ibss_pset; - struct iw_mgmt_data_rset bss_basic_rset; + struct wl3501_req req; u8 rssi; }; @@ -471,8 +466,10 @@ struct wl3501_md_req { u16 size; u8 pri; u8 service_class; - u8 daddr[ETH_ALEN]; - u8 saddr[ETH_ALEN]; + struct { + u8 daddr[ETH_ALEN]; + u8 saddr[ETH_ALEN]; + } addr; }; struct wl3501_md_ind { @@ -484,8 +481,10 @@ struct wl3501_md_ind { u8 reception; u8 pri; u8 service_class; - u8 daddr[ETH_ALEN]; - u8 saddr[ETH_ALEN]; + struct { + u8 daddr[ETH_ALEN]; + u8 saddr[ETH_ALEN]; + } addr; }; struct wl3501_md_confirm { diff --git a/drivers/net/wireless/wl3501_cs.c b/drivers/net/wireless/wl3501_cs.c index da62220b9c01a..f33ece9370473 100644 --- a/drivers/net/wireless/wl3501_cs.c +++ b/drivers/net/wireless/wl3501_cs.c @@ -468,6 +468,7 @@ static int wl3501_send_pkt(struct wl3501_card *this, u8 *data, u16 len) struct wl3501_md_req sig = { .sig_id = WL3501_SIG_MD_REQ, }; + size_t sig_addr_len = sizeof(sig.addr); u8 *pdata = (char *)data; int rc = -EIO; @@ -483,9 +484,9 @@ static int wl3501_send_pkt(struct wl3501_card *this, u8 *data, u16 len) goto out; } rc = 0; - memcpy(&sig.daddr[0], pdata, 12); - pktlen = len - 12; - pdata += 12; + memcpy(&sig.addr, pdata, sig_addr_len); + pktlen = len - sig_addr_len; + pdata += sig_addr_len; sig.data = bf; if (((*pdata) * 256 + (*(pdata + 1))) > 1500) { u8 addr4[ETH_ALEN] = { @@ -588,7 +589,7 @@ static int wl3501_mgmt_join(struct wl3501_card *this, u16 stas) struct wl3501_join_req sig = { .sig_id = WL3501_SIG_JOIN_REQ, .timeout = 10, - .ds_pset = { + .req.ds_pset = { .el = { .id = IW_MGMT_INFO_ELEMENT_DS_PARAMETER_SET, .len = 1, @@ -597,7 +598,7 @@ static int wl3501_mgmt_join(struct wl3501_card *this, u16 stas) }, }; - memcpy(&sig.beacon_period, &this->bss_set[stas].beacon_period, 72); + memcpy(&sig.req, &this->bss_set[stas].req, sizeof(sig.req)); return wl3501_esbq_exec(this, &sig, sizeof(sig)); } @@ -665,35 +666,37 @@ static void wl3501_mgmt_scan_confirm(struct wl3501_card *this, u16 addr) if (sig.status == WL3501_STATUS_SUCCESS) { pr_debug("success"); if ((this->net_type == IW_MODE_INFRA && - (sig.cap_info & WL3501_MGMT_CAPABILITY_ESS)) || + (sig.req.cap_info & WL3501_MGMT_CAPABILITY_ESS)) || (this->net_type == IW_MODE_ADHOC && - (sig.cap_info & WL3501_MGMT_CAPABILITY_IBSS)) || + (sig.req.cap_info & WL3501_MGMT_CAPABILITY_IBSS)) || this->net_type == IW_MODE_AUTO) { if (!this->essid.el.len) matchflag = 1; else if (this->essid.el.len == 3 && !memcmp(this->essid.essid, "ANY", 3)) matchflag = 1; - else if (this->essid.el.len != sig.ssid.el.len) + else if (this->essid.el.len != sig.req.ssid.el.len) matchflag = 0; - else if (memcmp(this->essid.essid, sig.ssid.essid, + else if (memcmp(this->essid.essid, sig.req.ssid.essid, this->essid.el.len)) matchflag = 0; else matchflag = 1; if (matchflag) { for (i = 0; i < this->bss_cnt; i++) { - if (ether_addr_equal_unaligned(this->bss_set[i].bssid, sig.bssid)) { + if (ether_addr_equal_unaligned(this->bss_set[i].req.bssid, + sig.req.bssid)) { matchflag = 0; break; } } } if (matchflag && (i < 20)) { - memcpy(&this->bss_set[i].beacon_period, - &sig.beacon_period, 73); + memcpy(&this->bss_set[i].req, + &sig.req, sizeof(sig.req)); this->bss_cnt++; this->rssi = sig.rssi; + this->bss_set[i].rssi = sig.rssi; } } } else if (sig.status == WL3501_STATUS_TIMEOUT) { @@ -885,19 +888,19 @@ static void wl3501_mgmt_join_confirm(struct net_device *dev, u16 addr) if (this->join_sta_bss < this->bss_cnt) { const int i = this->join_sta_bss; memcpy(this->bssid, - this->bss_set[i].bssid, ETH_ALEN); - this->chan = this->bss_set[i].ds_pset.chan; + this->bss_set[i].req.bssid, ETH_ALEN); + this->chan = this->bss_set[i].req.ds_pset.chan; iw_copy_mgmt_info_element(&this->keep_essid.el, - &this->bss_set[i].ssid.el); + &this->bss_set[i].req.ssid.el); wl3501_mgmt_auth(this); } } else { const int i = this->join_sta_bss; - memcpy(&this->bssid, &this->bss_set[i].bssid, ETH_ALEN); - this->chan = this->bss_set[i].ds_pset.chan; + memcpy(&this->bssid, &this->bss_set[i].req.bssid, ETH_ALEN); + this->chan = this->bss_set[i].req.ds_pset.chan; iw_copy_mgmt_info_element(&this->keep_essid.el, - &this->bss_set[i].ssid.el); + &this->bss_set[i].req.ssid.el); wl3501_online(dev); } } else { @@ -979,7 +982,8 @@ static inline void wl3501_md_ind_interrupt(struct net_device *dev, } else { skb->dev = dev; skb_reserve(skb, 2); /* IP headers on 16 bytes boundaries */ - skb_copy_to_linear_data(skb, (unsigned char *)&sig.daddr, 12); + skb_copy_to_linear_data(skb, (unsigned char *)&sig.addr, + sizeof(sig.addr)); wl3501_receive(this, skb->data, pkt_len); skb_put(skb, pkt_len); skb->protocol = eth_type_trans(skb, dev); @@ -1574,30 +1578,30 @@ static int wl3501_get_scan(struct net_device *dev, struct iw_request_info *info, for (i = 0; i < this->bss_cnt; ++i) { iwe.cmd = SIOCGIWAP; iwe.u.ap_addr.sa_family = ARPHRD_ETHER; - memcpy(iwe.u.ap_addr.sa_data, this->bss_set[i].bssid, ETH_ALEN); + memcpy(iwe.u.ap_addr.sa_data, this->bss_set[i].req.bssid, ETH_ALEN); current_ev = iwe_stream_add_event(info, current_ev, extra + IW_SCAN_MAX_DATA, &iwe, IW_EV_ADDR_LEN); iwe.cmd = SIOCGIWESSID; iwe.u.data.flags = 1; - iwe.u.data.length = this->bss_set[i].ssid.el.len; + iwe.u.data.length = this->bss_set[i].req.ssid.el.len; current_ev = iwe_stream_add_point(info, current_ev, extra + IW_SCAN_MAX_DATA, &iwe, - this->bss_set[i].ssid.essid); + this->bss_set[i].req.ssid.essid); iwe.cmd = SIOCGIWMODE; - iwe.u.mode = this->bss_set[i].bss_type; + iwe.u.mode = this->bss_set[i].req.bss_type; current_ev = iwe_stream_add_event(info, current_ev, extra + IW_SCAN_MAX_DATA, &iwe, IW_EV_UINT_LEN); iwe.cmd = SIOCGIWFREQ; - iwe.u.freq.m = this->bss_set[i].ds_pset.chan; + iwe.u.freq.m = this->bss_set[i].req.ds_pset.chan; iwe.u.freq.e = 0; current_ev = iwe_stream_add_event(info, current_ev, extra + IW_SCAN_MAX_DATA, &iwe, IW_EV_FREQ_LEN); iwe.cmd = SIOCGIWENCODE; - if (this->bss_set[i].cap_info & WL3501_MGMT_CAPABILITY_PRIVACY) + if (this->bss_set[i].req.cap_info & WL3501_MGMT_CAPABILITY_PRIVACY) iwe.u.data.flags = IW_ENCODE_ENABLED | IW_ENCODE_NOKEY; else iwe.u.data.flags = IW_ENCODE_DISABLED; diff --git a/drivers/nfc/pn533/pn533.c b/drivers/nfc/pn533/pn533.c index a0cc1cc452927..01da9331f4cb6 100644 --- a/drivers/nfc/pn533/pn533.c +++ b/drivers/nfc/pn533/pn533.c @@ -692,6 +692,9 @@ static bool pn533_target_type_a_is_valid(struct pn533_target_type_a *type_a, if (PN533_TYPE_A_SEL_CASCADE(type_a->sel_res) != 0) return false; + if (type_a->nfcid_len > NFC_NFCID1_MAXSIZE) + return false; + return true; } diff --git a/drivers/nvme/host/core.c b/drivers/nvme/host/core.c index 513dd1e2aac76..e64310f2296f8 100644 --- a/drivers/nvme/host/core.c +++ b/drivers/nvme/host/core.c @@ -2091,7 +2091,8 @@ static void nvme_set_latency_tolerance(struct device *dev, s32 val) if (ctrl->ps_max_latency_us != latency) { ctrl->ps_max_latency_us = latency; - nvme_configure_apst(ctrl); + if (ctrl->state == NVME_CTRL_LIVE) + nvme_configure_apst(ctrl); } } diff --git a/drivers/nvme/host/multipath.c b/drivers/nvme/host/multipath.c index 4ef05fe00dace..64f699a1afd72 100644 --- a/drivers/nvme/host/multipath.c +++ b/drivers/nvme/host/multipath.c @@ -516,6 +516,10 @@ void nvme_mpath_add_disk(struct nvme_ns *ns, struct nvme_id_ns *id) if (desc.state) { /* found the group desc: update */ nvme_update_ns_ana_state(&desc, ns); + } else { + /* group desc not found: trigger a re-read */ + set_bit(NVME_NS_ANA_PENDING, &ns->flags); + queue_work(nvme_wq, &ns->ctrl->ana_work); } } else { mutex_lock(&ns->head->lock); diff --git a/drivers/of/fdt.c b/drivers/of/fdt.c index 21160a08ead4b..800ad252cf9c6 100644 --- a/drivers/of/fdt.c +++ b/drivers/of/fdt.c @@ -1172,16 +1172,8 @@ int __init __weak early_init_dt_mark_hotplug_memory_arch(u64 base, u64 size) int __init __weak early_init_dt_reserve_memory_arch(phys_addr_t base, phys_addr_t size, bool nomap) { - if (nomap) { - /* - * If the memory is already reserved (by another region), we - * should not allow it to be marked nomap. - */ - if (memblock_is_region_reserved(base, size)) - return -EBUSY; - - return memblock_mark_nomap(base, size); - } + if (nomap) + return memblock_remove(base, size); return memblock_reserve(base, size); } diff --git a/drivers/pci/controller/pci-thunder-ecam.c b/drivers/pci/controller/pci-thunder-ecam.c index 32d1d7b81ef4e..18715d2ce0229 100644 --- a/drivers/pci/controller/pci-thunder-ecam.c +++ b/drivers/pci/controller/pci-thunder-ecam.c @@ -116,7 +116,7 @@ static int thunder_ecam_p2_config_read(struct pci_bus *bus, unsigned int devfn, * the config space access window. Since we are working with * the high-order 32 bits, shift everything down by 32 bits. */ - node_bits = (cfg->res.start >> 32) & (1 << 12); + node_bits = upper_32_bits(cfg->res.start) & (1 << 12); v |= node_bits; set_val(v, where, size, val); diff --git a/drivers/pci/controller/pci-thunder-pem.c b/drivers/pci/controller/pci-thunder-pem.c index f127ce8bd4ef3..1650ec2c35f9a 100644 --- a/drivers/pci/controller/pci-thunder-pem.c +++ b/drivers/pci/controller/pci-thunder-pem.c @@ -11,6 +11,7 @@ #include #include #include +#include #include "../pci.h" #if defined(CONFIG_PCI_HOST_THUNDER_PEM) || (defined(CONFIG_ACPI) && defined(CONFIG_PCI_QUIRKS)) @@ -314,9 +315,9 @@ static int thunder_pem_init(struct device *dev, struct pci_config_window *cfg, * structure here for the BAR. */ bar4_start = res_pem->start + 0xf00000; - pem_pci->ea_entry[0] = (u32)bar4_start | 2; - pem_pci->ea_entry[1] = (u32)(res_pem->end - bar4_start) & ~3u; - pem_pci->ea_entry[2] = (u32)(bar4_start >> 32); + pem_pci->ea_entry[0] = lower_32_bits(bar4_start) | 2; + pem_pci->ea_entry[1] = lower_32_bits(res_pem->end - bar4_start) & ~3u; + pem_pci->ea_entry[2] = upper_32_bits(bar4_start); cfg->priv = pem_pci; return 0; @@ -324,9 +325,9 @@ static int thunder_pem_init(struct device *dev, struct pci_config_window *cfg, #if defined(CONFIG_ACPI) && defined(CONFIG_PCI_QUIRKS) -#define PEM_RES_BASE 0x87e0c0000000UL -#define PEM_NODE_MASK GENMASK(45, 44) -#define PEM_INDX_MASK GENMASK(26, 24) +#define PEM_RES_BASE 0x87e0c0000000ULL +#define PEM_NODE_MASK GENMASK_ULL(45, 44) +#define PEM_INDX_MASK GENMASK_ULL(26, 24) #define PEM_MIN_DOM_IN_NODE 4 #define PEM_MAX_DOM_IN_NODE 10 diff --git a/drivers/pci/controller/pcie-iproc-msi.c b/drivers/pci/controller/pcie-iproc-msi.c index ea612382599cf..dc953c73cb56a 100644 --- a/drivers/pci/controller/pcie-iproc-msi.c +++ b/drivers/pci/controller/pcie-iproc-msi.c @@ -271,7 +271,7 @@ static int iproc_msi_irq_domain_alloc(struct irq_domain *domain, NULL, NULL); } - return hwirq; + return 0; } static void iproc_msi_irq_domain_free(struct irq_domain *domain, diff --git a/drivers/pci/endpoint/functions/pci-epf-test.c b/drivers/pci/endpoint/functions/pci-epf-test.c index 4bbd26e8a9e2f..09a1e449cd1c6 100644 --- a/drivers/pci/endpoint/functions/pci-epf-test.c +++ b/drivers/pci/endpoint/functions/pci-epf-test.c @@ -572,6 +572,7 @@ static int __init pci_epf_test_init(void) WQ_MEM_RECLAIM | WQ_HIGHPRI, 0); ret = pci_epf_register_driver(&test_driver); if (ret) { + destroy_workqueue(kpcitest_workqueue); pr_err("Failed to register pci epf test driver --> %d\n", ret); return ret; } @@ -582,6 +583,8 @@ module_init(pci_epf_test_init); static void __exit pci_epf_test_exit(void) { + if (kpcitest_workqueue) + destroy_workqueue(kpcitest_workqueue); pci_epf_unregister_driver(&test_driver); } module_exit(pci_epf_test_exit); diff --git a/drivers/pci/hotplug/acpiphp_glue.c b/drivers/pci/hotplug/acpiphp_glue.c index be35bbfa69687..3d8844e7090a8 100644 --- a/drivers/pci/hotplug/acpiphp_glue.c +++ b/drivers/pci/hotplug/acpiphp_glue.c @@ -540,6 +540,7 @@ static void enable_slot(struct acpiphp_slot *slot, bool bridge) slot->flags &= ~SLOT_ENABLED; continue; } + pci_dev_put(dev); } } diff --git a/drivers/pci/pci.c b/drivers/pci/pci.c index 9ebf32de85757..3d59bbe4a5d56 100644 --- a/drivers/pci/pci.c +++ b/drivers/pci/pci.c @@ -1585,20 +1585,10 @@ static int pci_enable_device_flags(struct pci_dev *dev, unsigned long flags) int err; int i, bars = 0; - /* - * Power state could be unknown at this point, either due to a fresh - * boot or a device removal call. So get the current power state - * so that things like MSI message writing will behave as expected - * (e.g. if the device really is in D0 at enable time). - */ - if (dev->pm_cap) { - u16 pmcsr; - pci_read_config_word(dev, dev->pm_cap + PCI_PM_CTRL, &pmcsr); - dev->current_state = (pmcsr & PCI_PM_CTRL_STATE_MASK); - } - - if (atomic_inc_return(&dev->enable_cnt) > 1) + if (atomic_inc_return(&dev->enable_cnt) > 1) { + pci_update_current_state(dev, dev->current_state); return 0; /* already enabled */ + } bridge = pci_upstream_bridge(dev); if (bridge) diff --git a/drivers/pci/pci.h b/drivers/pci/pci.h index e9ede82ee2c25..39725b71300f8 100644 --- a/drivers/pci/pci.h +++ b/drivers/pci/pci.h @@ -473,6 +473,12 @@ static inline int pci_dev_specific_reset(struct pci_dev *dev, int probe) #if defined(CONFIG_PCI_QUIRKS) && defined(CONFIG_ARM64) int acpi_get_rc_resources(struct device *dev, const char *hid, u16 segment, struct resource *res); +#else +static inline int acpi_get_rc_resources(struct device *dev, const char *hid, + u16 segment, struct resource *res) +{ + return -ENODEV; +} #endif u32 pci_rebar_get_possible_sizes(struct pci_dev *pdev, int bar); diff --git a/drivers/pci/probe.c b/drivers/pci/probe.c index 9a5b6a8e2502f..113b7bdf86dd9 100644 --- a/drivers/pci/probe.c +++ b/drivers/pci/probe.c @@ -2359,6 +2359,7 @@ static struct pci_dev *pci_scan_device(struct pci_bus *bus, int devfn) pci_set_of_node(dev); if (pci_setup_device(dev)) { + pci_release_of_node(dev); pci_bus_put(dev->bus); kfree(dev); return NULL; diff --git a/drivers/perf/arm_pmu_platform.c b/drivers/perf/arm_pmu_platform.c index 96075cecb0aec..199293450acfc 100644 --- a/drivers/perf/arm_pmu_platform.c +++ b/drivers/perf/arm_pmu_platform.c @@ -236,7 +236,7 @@ int arm_pmu_device_probe(struct platform_device *pdev, ret = armpmu_register(pmu); if (ret) - goto out_free; + goto out_free_irqs; return 0; diff --git a/drivers/phy/marvell/Kconfig b/drivers/phy/marvell/Kconfig index 68e3212254005..ed4d3904e53f9 100644 --- a/drivers/phy/marvell/Kconfig +++ b/drivers/phy/marvell/Kconfig @@ -2,8 +2,8 @@ # Phy drivers for Marvell platforms # config ARMADA375_USBCLUSTER_PHY - def_bool y - depends on MACH_ARMADA_375 || COMPILE_TEST + bool "Armada 375 USB cluster PHY support" if COMPILE_TEST + default y if MACH_ARMADA_375 depends on OF && HAS_IOMEM select GENERIC_PHY diff --git a/drivers/phy/ti/phy-twl4030-usb.c b/drivers/phy/ti/phy-twl4030-usb.c index c267afb68f077..ea7564392108c 100644 --- a/drivers/phy/ti/phy-twl4030-usb.c +++ b/drivers/phy/ti/phy-twl4030-usb.c @@ -801,7 +801,7 @@ static int twl4030_usb_remove(struct platform_device *pdev) usb_remove_phy(&twl->phy); pm_runtime_get_sync(twl->dev); - cancel_delayed_work(&twl->id_workaround_work); + cancel_delayed_work_sync(&twl->id_workaround_work); device_remove_file(twl->dev, &dev_attr_vbus); /* set transceiver mode to power on defaults */ diff --git a/drivers/pinctrl/pinctrl-ingenic.c b/drivers/pinctrl/pinctrl-ingenic.c index a5accffbc8c91..babf6d011264e 100644 --- a/drivers/pinctrl/pinctrl-ingenic.c +++ b/drivers/pinctrl/pinctrl-ingenic.c @@ -642,7 +642,8 @@ static int ingenic_pinconf_set(struct pinctrl_dev *pctldev, unsigned int pin, break; default: - unreachable(); + /* unreachable */ + break; } } diff --git a/drivers/pinctrl/samsung/pinctrl-exynos.c b/drivers/pinctrl/samsung/pinctrl-exynos.c index 24956f6c6324f..7f764f751c4f1 100644 --- a/drivers/pinctrl/samsung/pinctrl-exynos.c +++ b/drivers/pinctrl/samsung/pinctrl-exynos.c @@ -55,7 +55,7 @@ static void exynos_irq_mask(struct irq_data *irqd) struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip); struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd); unsigned long reg_mask = our_chip->eint_mask + bank->eint_offset; - unsigned long mask; + unsigned int mask; unsigned long flags; spin_lock_irqsave(&bank->slock, flags); @@ -83,7 +83,7 @@ static void exynos_irq_unmask(struct irq_data *irqd) struct exynos_irq_chip *our_chip = to_exynos_irq_chip(chip); struct samsung_pin_bank *bank = irq_data_get_irq_chip_data(irqd); unsigned long reg_mask = our_chip->eint_mask + bank->eint_offset; - unsigned long mask; + unsigned int mask; unsigned long flags; /* @@ -482,7 +482,7 @@ static void exynos_irq_eint0_15(struct irq_desc *desc) chained_irq_exit(chip, desc); } -static inline void exynos_irq_demux_eint(unsigned long pend, +static inline void exynos_irq_demux_eint(unsigned int pend, struct irq_domain *domain) { unsigned int irq; @@ -499,8 +499,8 @@ static void exynos_irq_demux_eint16_31(struct irq_desc *desc) { struct irq_chip *chip = irq_desc_get_chip(desc); struct exynos_muxed_weint_data *eintd = irq_desc_get_handler_data(desc); - unsigned long pend; - unsigned long mask; + unsigned int pend; + unsigned int mask; int i; chained_irq_enter(chip, desc); diff --git a/drivers/platform/x86/pmc_atom.c b/drivers/platform/x86/pmc_atom.c index 26351e9e0aafe..682fc49d172cb 100644 --- a/drivers/platform/x86/pmc_atom.c +++ b/drivers/platform/x86/pmc_atom.c @@ -423,34 +423,10 @@ static const struct dmi_system_id critclk_systems[] = { }, { /* pmc_plt_clk* - are used for ethernet controllers */ - .ident = "Beckhoff CB3163", + .ident = "Beckhoff Baytrail", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"), - DMI_MATCH(DMI_BOARD_NAME, "CB3163"), - }, - }, - { - /* pmc_plt_clk* - are used for ethernet controllers */ - .ident = "Beckhoff CB4063", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"), - DMI_MATCH(DMI_BOARD_NAME, "CB4063"), - }, - }, - { - /* pmc_plt_clk* - are used for ethernet controllers */ - .ident = "Beckhoff CB6263", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"), - DMI_MATCH(DMI_BOARD_NAME, "CB6263"), - }, - }, - { - /* pmc_plt_clk* - are used for ethernet controllers */ - .ident = "Beckhoff CB6363", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "Beckhoff Automation"), - DMI_MATCH(DMI_BOARD_NAME, "CB6363"), + DMI_MATCH(DMI_PRODUCT_FAMILY, "CBxx63"), }, }, { diff --git a/drivers/power/supply/bq27xxx_battery.c b/drivers/power/supply/bq27xxx_battery.c index 93e3d9c747aa0..b7dc881268666 100644 --- a/drivers/power/supply/bq27xxx_battery.c +++ b/drivers/power/supply/bq27xxx_battery.c @@ -1490,27 +1490,6 @@ static int bq27xxx_battery_read_time(struct bq27xxx_device_info *di, u8 reg) return tval * 60; } -/* - * Read an average power register. - * Return < 0 if something fails. - */ -static int bq27xxx_battery_read_pwr_avg(struct bq27xxx_device_info *di) -{ - int tval; - - tval = bq27xxx_read(di, BQ27XXX_REG_AP, false); - if (tval < 0) { - dev_err(di->dev, "error reading average power register %02x: %d\n", - BQ27XXX_REG_AP, tval); - return tval; - } - - if (di->opts & BQ27XXX_O_ZERO) - return (tval * BQ27XXX_POWER_CONSTANT) / BQ27XXX_RS; - else - return tval; -} - /* * Returns true if a battery over temperature condition is detected */ @@ -1607,8 +1586,6 @@ void bq27xxx_battery_update(struct bq27xxx_device_info *di) } if (di->regs[BQ27XXX_REG_CYCT] != INVALID_REG_ADDR) cache.cycle_count = bq27xxx_battery_read_cyct(di); - if (di->regs[BQ27XXX_REG_AP] != INVALID_REG_ADDR) - cache.power_avg = bq27xxx_battery_read_pwr_avg(di); /* We only have to read charge design full once */ if (di->charge_design_full <= 0) @@ -1670,6 +1647,32 @@ static int bq27xxx_battery_current(struct bq27xxx_device_info *di, return 0; } +/* + * Get the average power in µW + * Return < 0 if something fails. + */ +static int bq27xxx_battery_pwr_avg(struct bq27xxx_device_info *di, + union power_supply_propval *val) +{ + int power; + + power = bq27xxx_read(di, BQ27XXX_REG_AP, false); + if (power < 0) { + dev_err(di->dev, + "error reading average power register %02x: %d\n", + BQ27XXX_REG_AP, power); + return power; + } + + if (di->opts & BQ27XXX_O_ZERO) + val->intval = (power * BQ27XXX_POWER_CONSTANT) / BQ27XXX_RS; + else + /* Other gauges return a signed value in units of 10mW */ + val->intval = (int)((s16)power) * 10000; + + return 0; +} + static int bq27xxx_battery_status(struct bq27xxx_device_info *di, union power_supply_propval *val) { @@ -1837,7 +1840,7 @@ static int bq27xxx_battery_get_property(struct power_supply *psy, ret = bq27xxx_simple_value(di->cache.energy, val); break; case POWER_SUPPLY_PROP_POWER_AVG: - ret = bq27xxx_simple_value(di->cache.power_avg, val); + ret = bq27xxx_battery_pwr_avg(di, val); break; case POWER_SUPPLY_PROP_HEALTH: ret = bq27xxx_simple_value(di->cache.health, val); diff --git a/drivers/power/supply/generic-adc-battery.c b/drivers/power/supply/generic-adc-battery.c index bc462d1ec9630..97b0e873e87d2 100644 --- a/drivers/power/supply/generic-adc-battery.c +++ b/drivers/power/supply/generic-adc-battery.c @@ -382,7 +382,7 @@ static int gab_remove(struct platform_device *pdev) } kfree(adc_bat->psy_desc.properties); - cancel_delayed_work(&adc_bat->bat_work); + cancel_delayed_work_sync(&adc_bat->bat_work); return 0; } diff --git a/drivers/power/supply/lp8788-charger.c b/drivers/power/supply/lp8788-charger.c index b8f7dac7ac3fe..6dcabbeccde12 100644 --- a/drivers/power/supply/lp8788-charger.c +++ b/drivers/power/supply/lp8788-charger.c @@ -529,7 +529,7 @@ static int lp8788_set_irqs(struct platform_device *pdev, ret = request_threaded_irq(virq, NULL, lp8788_charger_irq_thread, - 0, name, pchg); + IRQF_ONESHOT, name, pchg); if (ret) break; } diff --git a/drivers/power/supply/pm2301_charger.c b/drivers/power/supply/pm2301_charger.c index 78561b6884fc7..9ef218d76aa9c 100644 --- a/drivers/power/supply/pm2301_charger.c +++ b/drivers/power/supply/pm2301_charger.c @@ -1098,7 +1098,7 @@ static int pm2xxx_wall_charger_probe(struct i2c_client *i2c_client, ret = request_threaded_irq(gpio_to_irq(pm2->pdata->gpio_irq_number), NULL, pm2xxx_charger_irq[0].isr, - pm2->pdata->irq_type, + pm2->pdata->irq_type | IRQF_ONESHOT, pm2xxx_charger_irq[0].name, pm2); if (ret != 0) { diff --git a/drivers/power/supply/s3c_adc_battery.c b/drivers/power/supply/s3c_adc_battery.c index 3d00b35cafc9e..8be31f80035c6 100644 --- a/drivers/power/supply/s3c_adc_battery.c +++ b/drivers/power/supply/s3c_adc_battery.c @@ -394,7 +394,7 @@ static int s3c_adc_bat_remove(struct platform_device *pdev) gpio_free(pdata->gpio_charge_finished); } - cancel_delayed_work(&bat_work); + cancel_delayed_work_sync(&bat_work); if (pdata->exit) pdata->exit(); diff --git a/drivers/power/supply/tps65090-charger.c b/drivers/power/supply/tps65090-charger.c index 1b4b5e09538e1..297bf58f0d4fb 100644 --- a/drivers/power/supply/tps65090-charger.c +++ b/drivers/power/supply/tps65090-charger.c @@ -311,7 +311,7 @@ static int tps65090_charger_probe(struct platform_device *pdev) if (irq != -ENXIO) { ret = devm_request_threaded_irq(&pdev->dev, irq, NULL, - tps65090_charger_isr, 0, "tps65090-charger", cdata); + tps65090_charger_isr, IRQF_ONESHOT, "tps65090-charger", cdata); if (ret) { dev_err(cdata->dev, "Unable to register irq %d err %d\n", irq, diff --git a/drivers/power/supply/tps65217_charger.c b/drivers/power/supply/tps65217_charger.c index 814c2b81fdfec..ba33d1617e0b6 100644 --- a/drivers/power/supply/tps65217_charger.c +++ b/drivers/power/supply/tps65217_charger.c @@ -238,7 +238,7 @@ static int tps65217_charger_probe(struct platform_device *pdev) for (i = 0; i < NUM_CHARGER_IRQS; i++) { ret = devm_request_threaded_irq(&pdev->dev, irq[i], NULL, tps65217_charger_irq, - 0, "tps65217-charger", + IRQF_ONESHOT, "tps65217-charger", charger); if (ret) { dev_err(charger->dev, diff --git a/drivers/rpmsg/qcom_glink_native.c b/drivers/rpmsg/qcom_glink_native.c index a755f85686e53..8fa0f0eaaf430 100644 --- a/drivers/rpmsg/qcom_glink_native.c +++ b/drivers/rpmsg/qcom_glink_native.c @@ -857,6 +857,7 @@ static int qcom_glink_rx_data(struct qcom_glink *glink, size_t avail) dev_err(glink->dev, "no intent found for channel %s intent %d", channel->name, liid); + ret = -ENOENT; goto advance_rx; } } diff --git a/drivers/rtc/rtc-ds1307.c b/drivers/rtc/rtc-ds1307.c index ebd59e86a567b..94d31779933f1 100644 --- a/drivers/rtc/rtc-ds1307.c +++ b/drivers/rtc/rtc-ds1307.c @@ -434,7 +434,11 @@ static int ds1307_get_time(struct device *dev, struct rtc_time *t) t->tm_min = bcd2bin(regs[DS1307_REG_MIN] & 0x7f); tmp = regs[DS1307_REG_HOUR] & 0x3f; t->tm_hour = bcd2bin(tmp); - t->tm_wday = bcd2bin(regs[DS1307_REG_WDAY] & 0x07) - 1; + /* rx8130 is bit position, not BCD */ + if (ds1307->type == rx_8130) + t->tm_wday = fls(regs[DS1307_REG_WDAY] & 0x7f); + else + t->tm_wday = bcd2bin(regs[DS1307_REG_WDAY] & 0x07) - 1; t->tm_mday = bcd2bin(regs[DS1307_REG_MDAY] & 0x3f); tmp = regs[DS1307_REG_MONTH] & 0x1f; t->tm_mon = bcd2bin(tmp) - 1; @@ -481,7 +485,11 @@ static int ds1307_set_time(struct device *dev, struct rtc_time *t) regs[DS1307_REG_SECS] = bin2bcd(t->tm_sec); regs[DS1307_REG_MIN] = bin2bcd(t->tm_min); regs[DS1307_REG_HOUR] = bin2bcd(t->tm_hour); - regs[DS1307_REG_WDAY] = bin2bcd(t->tm_wday + 1); + /* rx8130 is bit position, not BCD */ + if (ds1307->type == rx_8130) + regs[DS1307_REG_WDAY] = 1 << t->tm_wday; + else + regs[DS1307_REG_WDAY] = bin2bcd(t->tm_wday + 1); regs[DS1307_REG_MDAY] = bin2bcd(t->tm_mday); regs[DS1307_REG_MONTH] = bin2bcd(t->tm_mon + 1); diff --git a/drivers/scsi/device_handler/scsi_dh_alua.c b/drivers/scsi/device_handler/scsi_dh_alua.c index 60c48dc5d9453..efd2b43125286 100644 --- a/drivers/scsi/device_handler/scsi_dh_alua.c +++ b/drivers/scsi/device_handler/scsi_dh_alua.c @@ -579,10 +579,11 @@ static int alua_rtpg(struct scsi_device *sdev, struct alua_port_group *pg) * even though it shouldn't according to T10. * The retry without rtpg_ext_hdr_req set * handles this. + * Note: some arrays return a sense key of ILLEGAL_REQUEST + * with ASC 00h if they don't support the extended header. */ if (!(pg->flags & ALUA_RTPG_EXT_HDR_UNSUPP) && - sense_hdr.sense_key == ILLEGAL_REQUEST && - sense_hdr.asc == 0x24 && sense_hdr.ascq == 0) { + sense_hdr.sense_key == ILLEGAL_REQUEST) { pg->flags |= ALUA_RTPG_EXT_HDR_UNSUPP; goto retry; } diff --git a/drivers/scsi/ibmvscsi/ibmvfc.c b/drivers/scsi/ibmvscsi/ibmvfc.c index 50078a199fea0..b811436a46d01 100644 --- a/drivers/scsi/ibmvscsi/ibmvfc.c +++ b/drivers/scsi/ibmvscsi/ibmvfc.c @@ -506,8 +506,17 @@ static void ibmvfc_set_host_action(struct ibmvfc_host *vhost, if (vhost->action == IBMVFC_HOST_ACTION_ALLOC_TGTS) vhost->action = action; break; + case IBMVFC_HOST_ACTION_REENABLE: + case IBMVFC_HOST_ACTION_RESET: + vhost->action = action; + break; case IBMVFC_HOST_ACTION_INIT: case IBMVFC_HOST_ACTION_TGT_DEL: + case IBMVFC_HOST_ACTION_LOGO: + case IBMVFC_HOST_ACTION_QUERY_TGTS: + case IBMVFC_HOST_ACTION_TGT_DEL_FAILED: + case IBMVFC_HOST_ACTION_NONE: + default: switch (vhost->action) { case IBMVFC_HOST_ACTION_RESET: case IBMVFC_HOST_ACTION_REENABLE: @@ -517,15 +526,6 @@ static void ibmvfc_set_host_action(struct ibmvfc_host *vhost, break; } break; - case IBMVFC_HOST_ACTION_LOGO: - case IBMVFC_HOST_ACTION_QUERY_TGTS: - case IBMVFC_HOST_ACTION_TGT_DEL_FAILED: - case IBMVFC_HOST_ACTION_NONE: - case IBMVFC_HOST_ACTION_RESET: - case IBMVFC_HOST_ACTION_REENABLE: - default: - vhost->action = action; - break; } } @@ -4346,26 +4346,45 @@ static void ibmvfc_do_work(struct ibmvfc_host *vhost) case IBMVFC_HOST_ACTION_INIT_WAIT: break; case IBMVFC_HOST_ACTION_RESET: - vhost->action = IBMVFC_HOST_ACTION_TGT_DEL; spin_unlock_irqrestore(vhost->host->host_lock, flags); rc = ibmvfc_reset_crq(vhost); + spin_lock_irqsave(vhost->host->host_lock, flags); - if (rc == H_CLOSED) + if (!rc || rc == H_CLOSED) vio_enable_interrupts(to_vio_dev(vhost->dev)); - if (rc || (rc = ibmvfc_send_crq_init(vhost)) || - (rc = vio_enable_interrupts(to_vio_dev(vhost->dev)))) { - ibmvfc_link_down(vhost, IBMVFC_LINK_DEAD); - dev_err(vhost->dev, "Error after reset (rc=%d)\n", rc); + if (vhost->action == IBMVFC_HOST_ACTION_RESET) { + /* + * The only action we could have changed to would have + * been reenable, in which case, we skip the rest of + * this path and wait until we've done the re-enable + * before sending the crq init. + */ + vhost->action = IBMVFC_HOST_ACTION_TGT_DEL; + + if (rc || (rc = ibmvfc_send_crq_init(vhost)) || + (rc = vio_enable_interrupts(to_vio_dev(vhost->dev)))) { + ibmvfc_link_down(vhost, IBMVFC_LINK_DEAD); + dev_err(vhost->dev, "Error after reset (rc=%d)\n", rc); + } } break; case IBMVFC_HOST_ACTION_REENABLE: - vhost->action = IBMVFC_HOST_ACTION_TGT_DEL; spin_unlock_irqrestore(vhost->host->host_lock, flags); rc = ibmvfc_reenable_crq_queue(vhost); + spin_lock_irqsave(vhost->host->host_lock, flags); - if (rc || (rc = ibmvfc_send_crq_init(vhost))) { - ibmvfc_link_down(vhost, IBMVFC_LINK_DEAD); - dev_err(vhost->dev, "Error after enable (rc=%d)\n", rc); + if (vhost->action == IBMVFC_HOST_ACTION_REENABLE) { + /* + * The only action we could have changed to would have + * been reset, in which case, we skip the rest of this + * path and wait until we've done the reset before + * sending the crq init. + */ + vhost->action = IBMVFC_HOST_ACTION_TGT_DEL; + if (rc || (rc = ibmvfc_send_crq_init(vhost))) { + ibmvfc_link_down(vhost, IBMVFC_LINK_DEAD); + dev_err(vhost->dev, "Error after enable (rc=%d)\n", rc); + } } break; case IBMVFC_HOST_ACTION_LOGO: diff --git a/drivers/scsi/jazz_esp.c b/drivers/scsi/jazz_esp.c index 6eb5ff3e2e611..7dfe4237e5e8e 100644 --- a/drivers/scsi/jazz_esp.c +++ b/drivers/scsi/jazz_esp.c @@ -170,7 +170,9 @@ static int esp_jazz_probe(struct platform_device *dev) if (!esp->command_block) goto fail_unmap_regs; - host->irq = platform_get_irq(dev, 0); + host->irq = err = platform_get_irq(dev, 0); + if (err < 0) + goto fail_unmap_command_block; err = request_irq(host->irq, scsi_esp_intr, IRQF_SHARED, "ESP", esp); if (err < 0) goto fail_unmap_command_block; diff --git a/drivers/scsi/libfc/fc_lport.c b/drivers/scsi/libfc/fc_lport.c index ff943f477d6f0..f653109d56af0 100644 --- a/drivers/scsi/libfc/fc_lport.c +++ b/drivers/scsi/libfc/fc_lport.c @@ -1741,7 +1741,7 @@ void fc_lport_flogi_resp(struct fc_seq *sp, struct fc_frame *fp, if (mfs < FC_SP_MIN_MAX_PAYLOAD || mfs > FC_SP_MAX_MAX_PAYLOAD) { FC_LPORT_DBG(lport, "FLOGI bad mfs:%hu response, " - "lport->mfs:%hu\n", mfs, lport->mfs); + "lport->mfs:%u\n", mfs, lport->mfs); fc_lport_error(lport, fp); goto out; } diff --git a/drivers/scsi/lpfc/lpfc_crtn.h b/drivers/scsi/lpfc/lpfc_crtn.h index bea24bc4410a7..1a0b1cb9de787 100644 --- a/drivers/scsi/lpfc/lpfc_crtn.h +++ b/drivers/scsi/lpfc/lpfc_crtn.h @@ -56,9 +56,6 @@ void lpfc_register_new_vport(struct lpfc_hba *, struct lpfc_vport *, void lpfc_unreg_vpi(struct lpfc_hba *, uint16_t, LPFC_MBOXQ_t *); void lpfc_init_link(struct lpfc_hba *, LPFC_MBOXQ_t *, uint32_t, uint32_t); void lpfc_request_features(struct lpfc_hba *, struct lpfcMboxq *); -void lpfc_supported_pages(struct lpfcMboxq *); -void lpfc_pc_sli4_params(struct lpfcMboxq *); -int lpfc_pc_sli4_params_get(struct lpfc_hba *, LPFC_MBOXQ_t *); int lpfc_sli4_mbox_rsrc_extent(struct lpfc_hba *, struct lpfcMboxq *, uint16_t, uint16_t, bool); int lpfc_get_sli4_parameters(struct lpfc_hba *, LPFC_MBOXQ_t *); diff --git a/drivers/scsi/lpfc/lpfc_hw4.h b/drivers/scsi/lpfc/lpfc_hw4.h index 083f8c8706e51..a9bd12bfc15e5 100644 --- a/drivers/scsi/lpfc/lpfc_hw4.h +++ b/drivers/scsi/lpfc/lpfc_hw4.h @@ -122,6 +122,7 @@ struct lpfc_sli_intf { /* Define SLI4 Alignment requirements. */ #define LPFC_ALIGN_16_BYTE 16 #define LPFC_ALIGN_64_BYTE 64 +#define SLI4_PAGE_SIZE 4096 /* Define SLI4 specific definitions. */ #define LPFC_MQ_CQE_BYTE_OFFSET 256 @@ -2886,62 +2887,6 @@ struct lpfc_mbx_request_features { #define lpfc_mbx_rq_ftr_rsp_mrqp_WORD word3 }; -struct lpfc_mbx_supp_pages { - uint32_t word1; -#define qs_SHIFT 0 -#define qs_MASK 0x00000001 -#define qs_WORD word1 -#define wr_SHIFT 1 -#define wr_MASK 0x00000001 -#define wr_WORD word1 -#define pf_SHIFT 8 -#define pf_MASK 0x000000ff -#define pf_WORD word1 -#define cpn_SHIFT 16 -#define cpn_MASK 0x000000ff -#define cpn_WORD word1 - uint32_t word2; -#define list_offset_SHIFT 0 -#define list_offset_MASK 0x000000ff -#define list_offset_WORD word2 -#define next_offset_SHIFT 8 -#define next_offset_MASK 0x000000ff -#define next_offset_WORD word2 -#define elem_cnt_SHIFT 16 -#define elem_cnt_MASK 0x000000ff -#define elem_cnt_WORD word2 - uint32_t word3; -#define pn_0_SHIFT 24 -#define pn_0_MASK 0x000000ff -#define pn_0_WORD word3 -#define pn_1_SHIFT 16 -#define pn_1_MASK 0x000000ff -#define pn_1_WORD word3 -#define pn_2_SHIFT 8 -#define pn_2_MASK 0x000000ff -#define pn_2_WORD word3 -#define pn_3_SHIFT 0 -#define pn_3_MASK 0x000000ff -#define pn_3_WORD word3 - uint32_t word4; -#define pn_4_SHIFT 24 -#define pn_4_MASK 0x000000ff -#define pn_4_WORD word4 -#define pn_5_SHIFT 16 -#define pn_5_MASK 0x000000ff -#define pn_5_WORD word4 -#define pn_6_SHIFT 8 -#define pn_6_MASK 0x000000ff -#define pn_6_WORD word4 -#define pn_7_SHIFT 0 -#define pn_7_MASK 0x000000ff -#define pn_7_WORD word4 - uint32_t rsvd[27]; -#define LPFC_SUPP_PAGES 0 -#define LPFC_BLOCK_GUARD_PROFILES 1 -#define LPFC_SLI4_PARAMETERS 2 -}; - struct lpfc_mbx_memory_dump_type3 { uint32_t word1; #define lpfc_mbx_memory_dump_type3_type_SHIFT 0 @@ -3158,121 +3103,6 @@ struct user_eeprom { uint8_t reserved191[57]; }; -struct lpfc_mbx_pc_sli4_params { - uint32_t word1; -#define qs_SHIFT 0 -#define qs_MASK 0x00000001 -#define qs_WORD word1 -#define wr_SHIFT 1 -#define wr_MASK 0x00000001 -#define wr_WORD word1 -#define pf_SHIFT 8 -#define pf_MASK 0x000000ff -#define pf_WORD word1 -#define cpn_SHIFT 16 -#define cpn_MASK 0x000000ff -#define cpn_WORD word1 - uint32_t word2; -#define if_type_SHIFT 0 -#define if_type_MASK 0x00000007 -#define if_type_WORD word2 -#define sli_rev_SHIFT 4 -#define sli_rev_MASK 0x0000000f -#define sli_rev_WORD word2 -#define sli_family_SHIFT 8 -#define sli_family_MASK 0x000000ff -#define sli_family_WORD word2 -#define featurelevel_1_SHIFT 16 -#define featurelevel_1_MASK 0x000000ff -#define featurelevel_1_WORD word2 -#define featurelevel_2_SHIFT 24 -#define featurelevel_2_MASK 0x0000001f -#define featurelevel_2_WORD word2 - uint32_t word3; -#define fcoe_SHIFT 0 -#define fcoe_MASK 0x00000001 -#define fcoe_WORD word3 -#define fc_SHIFT 1 -#define fc_MASK 0x00000001 -#define fc_WORD word3 -#define nic_SHIFT 2 -#define nic_MASK 0x00000001 -#define nic_WORD word3 -#define iscsi_SHIFT 3 -#define iscsi_MASK 0x00000001 -#define iscsi_WORD word3 -#define rdma_SHIFT 4 -#define rdma_MASK 0x00000001 -#define rdma_WORD word3 - uint32_t sge_supp_len; -#define SLI4_PAGE_SIZE 4096 - uint32_t word5; -#define if_page_sz_SHIFT 0 -#define if_page_sz_MASK 0x0000ffff -#define if_page_sz_WORD word5 -#define loopbk_scope_SHIFT 24 -#define loopbk_scope_MASK 0x0000000f -#define loopbk_scope_WORD word5 -#define rq_db_window_SHIFT 28 -#define rq_db_window_MASK 0x0000000f -#define rq_db_window_WORD word5 - uint32_t word6; -#define eq_pages_SHIFT 0 -#define eq_pages_MASK 0x0000000f -#define eq_pages_WORD word6 -#define eqe_size_SHIFT 8 -#define eqe_size_MASK 0x000000ff -#define eqe_size_WORD word6 - uint32_t word7; -#define cq_pages_SHIFT 0 -#define cq_pages_MASK 0x0000000f -#define cq_pages_WORD word7 -#define cqe_size_SHIFT 8 -#define cqe_size_MASK 0x000000ff -#define cqe_size_WORD word7 - uint32_t word8; -#define mq_pages_SHIFT 0 -#define mq_pages_MASK 0x0000000f -#define mq_pages_WORD word8 -#define mqe_size_SHIFT 8 -#define mqe_size_MASK 0x000000ff -#define mqe_size_WORD word8 -#define mq_elem_cnt_SHIFT 16 -#define mq_elem_cnt_MASK 0x000000ff -#define mq_elem_cnt_WORD word8 - uint32_t word9; -#define wq_pages_SHIFT 0 -#define wq_pages_MASK 0x0000ffff -#define wq_pages_WORD word9 -#define wqe_size_SHIFT 8 -#define wqe_size_MASK 0x000000ff -#define wqe_size_WORD word9 - uint32_t word10; -#define rq_pages_SHIFT 0 -#define rq_pages_MASK 0x0000ffff -#define rq_pages_WORD word10 -#define rqe_size_SHIFT 8 -#define rqe_size_MASK 0x000000ff -#define rqe_size_WORD word10 - uint32_t word11; -#define hdr_pages_SHIFT 0 -#define hdr_pages_MASK 0x0000000f -#define hdr_pages_WORD word11 -#define hdr_size_SHIFT 8 -#define hdr_size_MASK 0x0000000f -#define hdr_size_WORD word11 -#define hdr_pp_align_SHIFT 16 -#define hdr_pp_align_MASK 0x0000ffff -#define hdr_pp_align_WORD word11 - uint32_t word12; -#define sgl_pages_SHIFT 0 -#define sgl_pages_MASK 0x0000000f -#define sgl_pages_WORD word12 -#define sgl_pp_align_SHIFT 16 -#define sgl_pp_align_MASK 0x0000ffff -#define sgl_pp_align_WORD word12 - uint32_t rsvd_13_63[51]; -}; #define SLI4_PAGE_ALIGN(addr) (((addr)+((SLI4_PAGE_SIZE)-1)) \ &(~((SLI4_PAGE_SIZE)-1))) @@ -3854,8 +3684,6 @@ struct lpfc_mqe { struct lpfc_mbx_post_hdr_tmpl hdr_tmpl; struct lpfc_mbx_query_fw_config query_fw_cfg; struct lpfc_mbx_set_beacon_config beacon_config; - struct lpfc_mbx_supp_pages supp_pages; - struct lpfc_mbx_pc_sli4_params sli4_params; struct lpfc_mbx_get_sli4_parameters get_sli4_parameters; struct lpfc_mbx_set_link_diag_state link_diag_state; struct lpfc_mbx_set_link_diag_loopback link_diag_loopback; diff --git a/drivers/scsi/lpfc/lpfc_init.c b/drivers/scsi/lpfc/lpfc_init.c index 57510a831735b..c6caacaa3e7a3 100644 --- a/drivers/scsi/lpfc/lpfc_init.c +++ b/drivers/scsi/lpfc/lpfc_init.c @@ -5854,8 +5854,6 @@ lpfc_sli4_driver_resource_setup(struct lpfc_hba *phba) LPFC_MBOXQ_t *mboxq; MAILBOX_t *mb; int rc, i, max_buf_size; - uint8_t pn_page[LPFC_MAX_SUPPORTED_PAGES] = {0}; - struct lpfc_mqe *mqe; int longs; int fof_vectors = 0; int extra; @@ -6150,32 +6148,6 @@ lpfc_sli4_driver_resource_setup(struct lpfc_hba *phba) lpfc_nvme_mod_param_dep(phba); - /* Get the Supported Pages if PORT_CAPABILITIES is supported by port. */ - lpfc_supported_pages(mboxq); - rc = lpfc_sli_issue_mbox(phba, mboxq, MBX_POLL); - if (!rc) { - mqe = &mboxq->u.mqe; - memcpy(&pn_page[0], ((uint8_t *)&mqe->un.supp_pages.word3), - LPFC_MAX_SUPPORTED_PAGES); - for (i = 0; i < LPFC_MAX_SUPPORTED_PAGES; i++) { - switch (pn_page[i]) { - case LPFC_SLI4_PARAMETERS: - phba->sli4_hba.pc_sli4_params.supported = 1; - break; - default: - break; - } - } - /* Read the port's SLI4 Parameters capabilities if supported. */ - if (phba->sli4_hba.pc_sli4_params.supported) - rc = lpfc_pc_sli4_params_get(phba, mboxq); - if (rc) { - mempool_free(mboxq, phba->mbox_mem_pool); - rc = -EIO; - goto out_free_bsmbx; - } - } - /* * Get sli4 parameters that override parameters from Port capabilities. * If this call fails, it isn't critical unless the SLI4 parameters come @@ -10517,78 +10489,6 @@ lpfc_sli4_hba_unset(struct lpfc_hba *phba) phba->pport->work_port_events = 0; } - /** - * lpfc_pc_sli4_params_get - Get the SLI4_PARAMS port capabilities. - * @phba: Pointer to HBA context object. - * @mboxq: Pointer to the mailboxq memory for the mailbox command response. - * - * This function is called in the SLI4 code path to read the port's - * sli4 capabilities. - * - * This function may be be called from any context that can block-wait - * for the completion. The expectation is that this routine is called - * typically from probe_one or from the online routine. - **/ -int -lpfc_pc_sli4_params_get(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) -{ - int rc; - struct lpfc_mqe *mqe; - struct lpfc_pc_sli4_params *sli4_params; - uint32_t mbox_tmo; - - rc = 0; - mqe = &mboxq->u.mqe; - - /* Read the port's SLI4 Parameters port capabilities */ - lpfc_pc_sli4_params(mboxq); - if (!phba->sli4_hba.intr_enable) - rc = lpfc_sli_issue_mbox(phba, mboxq, MBX_POLL); - else { - mbox_tmo = lpfc_mbox_tmo_val(phba, mboxq); - rc = lpfc_sli_issue_mbox_wait(phba, mboxq, mbox_tmo); - } - - if (unlikely(rc)) - return 1; - - sli4_params = &phba->sli4_hba.pc_sli4_params; - sli4_params->if_type = bf_get(if_type, &mqe->un.sli4_params); - sli4_params->sli_rev = bf_get(sli_rev, &mqe->un.sli4_params); - sli4_params->sli_family = bf_get(sli_family, &mqe->un.sli4_params); - sli4_params->featurelevel_1 = bf_get(featurelevel_1, - &mqe->un.sli4_params); - sli4_params->featurelevel_2 = bf_get(featurelevel_2, - &mqe->un.sli4_params); - sli4_params->proto_types = mqe->un.sli4_params.word3; - sli4_params->sge_supp_len = mqe->un.sli4_params.sge_supp_len; - sli4_params->if_page_sz = bf_get(if_page_sz, &mqe->un.sli4_params); - sli4_params->rq_db_window = bf_get(rq_db_window, &mqe->un.sli4_params); - sli4_params->loopbk_scope = bf_get(loopbk_scope, &mqe->un.sli4_params); - sli4_params->eq_pages_max = bf_get(eq_pages, &mqe->un.sli4_params); - sli4_params->eqe_size = bf_get(eqe_size, &mqe->un.sli4_params); - sli4_params->cq_pages_max = bf_get(cq_pages, &mqe->un.sli4_params); - sli4_params->cqe_size = bf_get(cqe_size, &mqe->un.sli4_params); - sli4_params->mq_pages_max = bf_get(mq_pages, &mqe->un.sli4_params); - sli4_params->mqe_size = bf_get(mqe_size, &mqe->un.sli4_params); - sli4_params->mq_elem_cnt = bf_get(mq_elem_cnt, &mqe->un.sli4_params); - sli4_params->wq_pages_max = bf_get(wq_pages, &mqe->un.sli4_params); - sli4_params->wqe_size = bf_get(wqe_size, &mqe->un.sli4_params); - sli4_params->rq_pages_max = bf_get(rq_pages, &mqe->un.sli4_params); - sli4_params->rqe_size = bf_get(rqe_size, &mqe->un.sli4_params); - sli4_params->hdr_pages_max = bf_get(hdr_pages, &mqe->un.sli4_params); - sli4_params->hdr_size = bf_get(hdr_size, &mqe->un.sli4_params); - sli4_params->hdr_pp_align = bf_get(hdr_pp_align, &mqe->un.sli4_params); - sli4_params->sgl_pages_max = bf_get(sgl_pages, &mqe->un.sli4_params); - sli4_params->sgl_pp_align = bf_get(sgl_pp_align, &mqe->un.sli4_params); - - /* Make sure that sge_supp_len can be handled by the driver */ - if (sli4_params->sge_supp_len > LPFC_MAX_SGE_SIZE) - sli4_params->sge_supp_len = LPFC_MAX_SGE_SIZE; - - return rc; -} - /** * lpfc_get_sli4_parameters - Get the SLI4 Config PARAMETERS. * @phba: Pointer to HBA context object. @@ -10647,7 +10547,8 @@ lpfc_get_sli4_parameters(struct lpfc_hba *phba, LPFC_MBOXQ_t *mboxq) else phba->sli3_options &= ~LPFC_SLI4_PHWQ_ENABLED; sli4_params->sge_supp_len = mbx_sli4_parameters->sge_supp_len; - sli4_params->loopbk_scope = bf_get(loopbk_scope, mbx_sli4_parameters); + sli4_params->loopbk_scope = bf_get(cfg_loopbk_scope, + mbx_sli4_parameters); sli4_params->oas_supported = bf_get(cfg_oas, mbx_sli4_parameters); sli4_params->cqv = bf_get(cfg_cqv, mbx_sli4_parameters); sli4_params->mqv = bf_get(cfg_mqv, mbx_sli4_parameters); diff --git a/drivers/scsi/lpfc/lpfc_mbox.c b/drivers/scsi/lpfc/lpfc_mbox.c index e6bf5e8bc7670..a4c382d2ce792 100644 --- a/drivers/scsi/lpfc/lpfc_mbox.c +++ b/drivers/scsi/lpfc/lpfc_mbox.c @@ -2622,39 +2622,3 @@ lpfc_resume_rpi(struct lpfcMboxq *mbox, struct lpfc_nodelist *ndlp) resume_rpi->event_tag = ndlp->phba->fc_eventTag; } -/** - * lpfc_supported_pages - Initialize the PORT_CAPABILITIES supported pages - * mailbox command. - * @mbox: pointer to lpfc mbox command to initialize. - * - * The PORT_CAPABILITIES supported pages mailbox command is issued to - * retrieve the particular feature pages supported by the port. - **/ -void -lpfc_supported_pages(struct lpfcMboxq *mbox) -{ - struct lpfc_mbx_supp_pages *supp_pages; - - memset(mbox, 0, sizeof(*mbox)); - supp_pages = &mbox->u.mqe.un.supp_pages; - bf_set(lpfc_mqe_command, &mbox->u.mqe, MBX_PORT_CAPABILITIES); - bf_set(cpn, supp_pages, LPFC_SUPP_PAGES); -} - -/** - * lpfc_pc_sli4_params - Initialize the PORT_CAPABILITIES SLI4 Params mbox cmd. - * @mbox: pointer to lpfc mbox command to initialize. - * - * The PORT_CAPABILITIES SLI4 parameters mailbox command is issued to - * retrieve the particular SLI4 features supported by the port. - **/ -void -lpfc_pc_sli4_params(struct lpfcMboxq *mbox) -{ - struct lpfc_mbx_pc_sli4_params *sli4_params; - - memset(mbox, 0, sizeof(*mbox)); - sli4_params = &mbox->u.mqe.un.sli4_params; - bf_set(lpfc_mqe_command, &mbox->u.mqe, MBX_PORT_CAPABILITIES); - bf_set(cpn, sli4_params, LPFC_SLI4_PARAMETERS); -} diff --git a/drivers/scsi/lpfc/lpfc_nportdisc.c b/drivers/scsi/lpfc/lpfc_nportdisc.c index 3dfed191252cf..9442fb30e7cd8 100644 --- a/drivers/scsi/lpfc/lpfc_nportdisc.c +++ b/drivers/scsi/lpfc/lpfc_nportdisc.c @@ -708,9 +708,14 @@ lpfc_rcv_logo(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp, } } else if ((!(ndlp->nlp_type & NLP_FABRIC) && ((ndlp->nlp_type & NLP_FCP_TARGET) || - !(ndlp->nlp_type & NLP_FCP_INITIATOR))) || + (ndlp->nlp_type & NLP_NVME_TARGET) || + (vport->fc_flag & FC_PT2PT))) || (ndlp->nlp_state == NLP_STE_ADISC_ISSUE)) { - /* Only try to re-login if this is NOT a Fabric Node */ + /* Only try to re-login if this is NOT a Fabric Node + * AND the remote NPORT is a FCP/NVME Target or we + * are in pt2pt mode. NLP_STE_ADISC_ISSUE is a special + * case for LOGO as a response to ADISC behavior. + */ mod_timer(&ndlp->nlp_delayfunc, jiffies + msecs_to_jiffies(1000 * 1)); spin_lock_irq(shost->host_lock); @@ -1738,8 +1743,6 @@ lpfc_cmpl_reglogin_reglogin_issue(struct lpfc_vport *vport, ndlp->nlp_last_elscmd = ELS_CMD_PLOGI; lpfc_issue_els_logo(vport, ndlp, 0); - ndlp->nlp_prev_state = NLP_STE_REG_LOGIN_ISSUE; - lpfc_nlp_set_state(vport, ndlp, NLP_STE_NPR_NODE); return ndlp->nlp_state; } diff --git a/drivers/scsi/lpfc/lpfc_nvmet.c b/drivers/scsi/lpfc/lpfc_nvmet.c index 5bc33817568ea..23ead17e60fe2 100644 --- a/drivers/scsi/lpfc/lpfc_nvmet.c +++ b/drivers/scsi/lpfc/lpfc_nvmet.c @@ -2912,7 +2912,6 @@ lpfc_nvmet_unsol_issue_abort(struct lpfc_hba *phba, bf_set(wqe_rcvoxid, &wqe_abts->xmit_sequence.wqe_com, xri); /* Word 10 */ - bf_set(wqe_dbde, &wqe_abts->xmit_sequence.wqe_com, 1); bf_set(wqe_iod, &wqe_abts->xmit_sequence.wqe_com, LPFC_WQE_IOD_WRITE); bf_set(wqe_lenloc, &wqe_abts->xmit_sequence.wqe_com, LPFC_WQE_LENLOC_WORD12); diff --git a/drivers/scsi/lpfc/lpfc_sli.c b/drivers/scsi/lpfc/lpfc_sli.c index a7b14875af5fa..f4633c9f8183f 100644 --- a/drivers/scsi/lpfc/lpfc_sli.c +++ b/drivers/scsi/lpfc/lpfc_sli.c @@ -17018,7 +17018,6 @@ lpfc_sli4_seq_abort_rsp_cmpl(struct lpfc_hba *phba, if (cmd_iocbq) { ndlp = (struct lpfc_nodelist *)cmd_iocbq->context1; lpfc_nlp_put(ndlp); - lpfc_nlp_not_used(ndlp); lpfc_sli_release_iocbq(phba, cmd_iocbq); } diff --git a/drivers/scsi/qla2xxx/qla_attr.c b/drivers/scsi/qla2xxx/qla_attr.c index 0ab9d2fd4a14a..d46a10d24ed4b 100644 --- a/drivers/scsi/qla2xxx/qla_attr.c +++ b/drivers/scsi/qla2xxx/qla_attr.c @@ -1934,6 +1934,8 @@ qla2x00_reset_host_stats(struct Scsi_Host *shost) vha->qla_stats.jiffies_at_last_reset = get_jiffies_64(); if (IS_FWI2_CAPABLE(ha)) { + int rval; + stats = dma_alloc_coherent(&ha->pdev->dev, sizeof(*stats), &stats_dma, GFP_KERNEL); if (!stats) { @@ -1943,7 +1945,11 @@ qla2x00_reset_host_stats(struct Scsi_Host *shost) } /* reset firmware statistics */ - qla24xx_get_isp_stats(base_vha, stats, stats_dma, BIT_0); + rval = qla24xx_get_isp_stats(base_vha, stats, stats_dma, BIT_0); + if (rval != QLA_SUCCESS) + ql_log(ql_log_warn, vha, 0x70de, + "Resetting ISP statistics failed: rval = %d\n", + rval); dma_free_coherent(&ha->pdev->dev, sizeof(*stats), stats, stats_dma); diff --git a/drivers/scsi/qla2xxx/qla_bsg.c b/drivers/scsi/qla2xxx/qla_bsg.c index 47f062e96e62c..eae1665729643 100644 --- a/drivers/scsi/qla2xxx/qla_bsg.c +++ b/drivers/scsi/qla2xxx/qla_bsg.c @@ -19,10 +19,11 @@ qla2x00_bsg_job_done(void *ptr, int res) struct bsg_job *bsg_job = sp->u.bsg_job; struct fc_bsg_reply *bsg_reply = bsg_job->reply; + sp->free(sp); + bsg_reply->result = res; bsg_job_done(bsg_job, bsg_reply->result, bsg_reply->reply_payload_rcv_len); - sp->free(sp); } void diff --git a/drivers/scsi/qla2xxx/qla_os.c b/drivers/scsi/qla2xxx/qla_os.c index 83ef790afb5df..7cbdd32a238d4 100644 --- a/drivers/scsi/qla2xxx/qla_os.c +++ b/drivers/scsi/qla2xxx/qla_os.c @@ -1028,8 +1028,6 @@ qla2xxx_mqueuecommand(struct Scsi_Host *host, struct scsi_cmnd *cmd, if (rval != QLA_SUCCESS) { ql_dbg(ql_dbg_io + ql_dbg_verbose, vha, 0x3078, "Start scsi failed rval=%d for cmd=%p.\n", rval, cmd); - if (rval == QLA_INTERFACE_ERROR) - goto qc24_free_sp_fail_command; goto qc24_host_busy_free_sp; } @@ -1044,11 +1042,6 @@ qc24_host_busy: qc24_target_busy: return SCSI_MLQUEUE_TARGET_BUSY; -qc24_free_sp_fail_command: - sp->free(sp); - CMD_SP(cmd) = NULL; - qla2xxx_rel_qpair_sp(sp->qpair, sp); - qc24_fail_command: cmd->scsi_done(cmd); diff --git a/drivers/scsi/sni_53c710.c b/drivers/scsi/sni_53c710.c index 3102a75984d3b..aed91afb79b68 100644 --- a/drivers/scsi/sni_53c710.c +++ b/drivers/scsi/sni_53c710.c @@ -71,6 +71,7 @@ static int snirm710_probe(struct platform_device *dev) struct NCR_700_Host_Parameters *hostdata; struct Scsi_Host *host; struct resource *res; + int rc; res = platform_get_resource(dev, IORESOURCE_MEM, 0); if (!res) @@ -96,7 +97,9 @@ static int snirm710_probe(struct platform_device *dev) goto out_kfree; host->this_id = 7; host->base = base; - host->irq = platform_get_irq(dev, 0); + host->irq = rc = platform_get_irq(dev, 0); + if (rc < 0) + goto out_put_host; if(request_irq(host->irq, NCR_700_intr, IRQF_SHARED, "snirm710", host)) { printk(KERN_ERR "snirm710: request_irq failed!\n"); goto out_put_host; diff --git a/drivers/scsi/sun3x_esp.c b/drivers/scsi/sun3x_esp.c index 0b1421cdf8a0e..f9aa95e48eeea 100644 --- a/drivers/scsi/sun3x_esp.c +++ b/drivers/scsi/sun3x_esp.c @@ -233,7 +233,9 @@ static int esp_sun3x_probe(struct platform_device *dev) if (!esp->command_block) goto fail_unmap_regs_dma; - host->irq = platform_get_irq(dev, 0); + host->irq = err = platform_get_irq(dev, 0); + if (err < 0) + goto fail_unmap_command_block; err = request_irq(host->irq, scsi_esp_intr, IRQF_SHARED, "SUN3X ESP", esp); if (err < 0) diff --git a/drivers/soc/qcom/mdt_loader.c b/drivers/soc/qcom/mdt_loader.c index 1c488024c6987..47dffe7736ff8 100644 --- a/drivers/soc/qcom/mdt_loader.c +++ b/drivers/soc/qcom/mdt_loader.c @@ -168,6 +168,14 @@ static int __qcom_mdt_load(struct device *dev, const struct firmware *fw, break; } + if (phdr->p_filesz > phdr->p_memsz) { + dev_err(dev, + "refusing to load segment %d with p_filesz > p_memsz\n", + i); + ret = -EINVAL; + break; + } + ptr = mem_region + offset; if (phdr->p_filesz) { @@ -179,6 +187,15 @@ static int __qcom_mdt_load(struct device *dev, const struct firmware *fw, break; } + if (seg_fw->size != phdr->p_filesz) { + dev_err(dev, + "failed to load segment %d from truncated file %s\n", + i, fw_name); + release_firmware(seg_fw); + ret = -EINVAL; + break; + } + release_firmware(seg_fw); } diff --git a/drivers/soundwire/bus.c b/drivers/soundwire/bus.c index df172bf3925f6..0089b606b70df 100644 --- a/drivers/soundwire/bus.c +++ b/drivers/soundwire/bus.c @@ -514,7 +514,7 @@ static int sdw_program_device_num(struct sdw_bus *bus) struct sdw_slave *slave, *_s; struct sdw_slave_id id; struct sdw_msg msg; - bool found = false; + bool found; int count = 0, ret; u64 addr; @@ -545,6 +545,7 @@ static int sdw_program_device_num(struct sdw_bus *bus) sdw_extract_slave_id(bus, addr, &id); + found = false; /* Now compare with entries */ list_for_each_entry_safe(slave, _s, &bus->slaves, node) { if (sdw_compare_devid(slave, id) == 0) { diff --git a/drivers/soundwire/stream.c b/drivers/soundwire/stream.c index 907a548645b75..42bc701e23040 100644 --- a/drivers/soundwire/stream.c +++ b/drivers/soundwire/stream.c @@ -1182,8 +1182,16 @@ int sdw_stream_add_slave(struct sdw_slave *slave, } ret = sdw_config_stream(&slave->dev, stream, stream_config, true); - if (ret) + if (ret) { + /* + * sdw_release_master_stream will release s_rt in slave_rt_list in + * stream_error case, but s_rt is only added to slave_rt_list + * when sdw_config_stream is successful, so free s_rt explicitly + * when sdw_config_stream is failed. + */ + kfree(s_rt); goto stream_error; + } list_add_tail(&s_rt->m_rt_node, &m_rt->slave_rt_list); diff --git a/drivers/spi/spi-dln2.c b/drivers/spi/spi-dln2.c index b62a99caacc06..a41adea486182 100644 --- a/drivers/spi/spi-dln2.c +++ b/drivers/spi/spi-dln2.c @@ -783,7 +783,7 @@ exit_free_master: static int dln2_spi_remove(struct platform_device *pdev) { - struct spi_master *master = spi_master_get(platform_get_drvdata(pdev)); + struct spi_master *master = platform_get_drvdata(pdev); struct dln2_spi *dln2 = spi_master_get_devdata(master); pm_runtime_disable(&pdev->dev); diff --git a/drivers/spi/spi-omap-100k.c b/drivers/spi/spi-omap-100k.c index 76a8425be227b..1eccdc4a45817 100644 --- a/drivers/spi/spi-omap-100k.c +++ b/drivers/spi/spi-omap-100k.c @@ -435,7 +435,7 @@ err: static int omap1_spi100k_remove(struct platform_device *pdev) { - struct spi_master *master = spi_master_get(platform_get_drvdata(pdev)); + struct spi_master *master = platform_get_drvdata(pdev); struct omap1_spi100k *spi100k = spi_master_get_devdata(master); pm_runtime_disable(&pdev->dev); @@ -449,7 +449,7 @@ static int omap1_spi100k_remove(struct platform_device *pdev) #ifdef CONFIG_PM static int omap1_spi100k_runtime_suspend(struct device *dev) { - struct spi_master *master = spi_master_get(dev_get_drvdata(dev)); + struct spi_master *master = dev_get_drvdata(dev); struct omap1_spi100k *spi100k = spi_master_get_devdata(master); clk_disable_unprepare(spi100k->ick); @@ -460,7 +460,7 @@ static int omap1_spi100k_runtime_suspend(struct device *dev) static int omap1_spi100k_runtime_resume(struct device *dev) { - struct spi_master *master = spi_master_get(dev_get_drvdata(dev)); + struct spi_master *master = dev_get_drvdata(dev); struct omap1_spi100k *spi100k = spi_master_get_devdata(master); int ret; diff --git a/drivers/spi/spi-ti-qspi.c b/drivers/spi/spi-ti-qspi.c index 73a08724034ba..c70b1790a959f 100644 --- a/drivers/spi/spi-ti-qspi.c +++ b/drivers/spi/spi-ti-qspi.c @@ -663,6 +663,17 @@ static int ti_qspi_runtime_resume(struct device *dev) return 0; } +static void ti_qspi_dma_cleanup(struct ti_qspi *qspi) +{ + if (qspi->rx_bb_addr) + dma_free_coherent(qspi->dev, QSPI_DMA_BUFFER_SIZE, + qspi->rx_bb_addr, + qspi->rx_bb_dma_addr); + + if (qspi->rx_chan) + dma_release_channel(qspi->rx_chan); +} + static const struct of_device_id ti_qspi_match[] = { {.compatible = "ti,dra7xxx-qspi" }, {.compatible = "ti,am4372-qspi" }, @@ -817,6 +828,8 @@ no_dma: if (!ret) return 0; + ti_qspi_dma_cleanup(qspi); + pm_runtime_disable(&pdev->dev); free_master: spi_master_put(master); @@ -835,12 +848,7 @@ static int ti_qspi_remove(struct platform_device *pdev) pm_runtime_put_sync(&pdev->dev); pm_runtime_disable(&pdev->dev); - if (qspi->rx_bb_addr) - dma_free_coherent(qspi->dev, QSPI_DMA_BUFFER_SIZE, - qspi->rx_bb_addr, - qspi->rx_bb_dma_addr); - if (qspi->rx_chan) - dma_release_channel(qspi->rx_chan); + ti_qspi_dma_cleanup(qspi); return 0; } diff --git a/drivers/spi/spi.c b/drivers/spi/spi.c index 7dabbc82b6463..bbe33016d3718 100644 --- a/drivers/spi/spi.c +++ b/drivers/spi/spi.c @@ -2084,6 +2084,7 @@ struct spi_controller *__devm_spi_alloc_controller(struct device *dev, ctlr = __spi_alloc_controller(dev, size, slave); if (ctlr) { + ctlr->devm_allocated = true; *ptr = ctlr; devres_add(dev, ptr); } else { @@ -2344,11 +2345,6 @@ int devm_spi_register_controller(struct device *dev, } EXPORT_SYMBOL_GPL(devm_spi_register_controller); -static int devm_spi_match_controller(struct device *dev, void *res, void *ctlr) -{ - return *(struct spi_controller **)res == ctlr; -} - static int __unregister(struct device *dev, void *null) { spi_unregister_device(to_spi_device(dev)); @@ -2395,8 +2391,7 @@ void spi_unregister_controller(struct spi_controller *ctlr) /* Release the last reference on the controller if its driver * has not yet been converted to devm_spi_alloc_master/slave(). */ - if (!devres_find(ctlr->dev.parent, devm_spi_release_controller, - devm_spi_match_controller, ctlr)) + if (!ctlr->devm_allocated) put_device(&ctlr->dev); /* free bus id */ diff --git a/drivers/staging/erofs/erofs_fs.h b/drivers/staging/erofs/erofs_fs.h index 7677da889f125..d8838ce669416 100644 --- a/drivers/staging/erofs/erofs_fs.h +++ b/drivers/staging/erofs/erofs_fs.h @@ -71,6 +71,9 @@ enum { #define EROFS_I_VERSION_BIT 0 __EROFS_BIT(EROFS_I_, DATA_MAPPING, VERSION); +#define EROFS_I_ALL \ + ((1 << (EROFS_I_DATA_MAPPING_BIT + EROFS_I_DATA_MAPPING_BITS)) - 1) + struct erofs_inode_v1 { /* 0 */__le16 i_advise; diff --git a/drivers/staging/erofs/inode.c b/drivers/staging/erofs/inode.c index a43abd530cc10..02398c7eb4a40 100644 --- a/drivers/staging/erofs/inode.c +++ b/drivers/staging/erofs/inode.c @@ -48,6 +48,12 @@ static struct page *read_inode(struct inode *inode, unsigned int *ofs) v1 = page_address(page) + *ofs; ifmt = le16_to_cpu(v1->i_advise); + if (ifmt & ~EROFS_I_ALL) { + errln("unsupported i_format %u of nid %llu", ifmt, vi->nid); + err = -EOPNOTSUPP; + goto err_out; + } + vi->data_mapping_mode = __inode_data_mapping(ifmt); if (unlikely(vi->data_mapping_mode >= EROFS_INODE_LAYOUT_MAX)) { errln("unknown data mapping mode %u of nid %llu", diff --git a/drivers/staging/greybus/uart.c b/drivers/staging/greybus/uart.c index f36d470aed241..2343914f7548a 100644 --- a/drivers/staging/greybus/uart.c +++ b/drivers/staging/greybus/uart.c @@ -656,8 +656,6 @@ static int set_serial_info(struct gb_tty *gb_tty, if ((close_delay != gb_tty->port.close_delay) || (closing_wait != gb_tty->port.closing_wait)) retval = -EPERM; - else - retval = -EOPNOTSUPP; } else { gb_tty->port.close_delay = close_delay; gb_tty->port.closing_wait = closing_wait; diff --git a/drivers/staging/media/omap4iss/iss.c b/drivers/staging/media/omap4iss/iss.c index b1036baebb035..d796e754610cb 100644 --- a/drivers/staging/media/omap4iss/iss.c +++ b/drivers/staging/media/omap4iss/iss.c @@ -1244,8 +1244,10 @@ static int iss_probe(struct platform_device *pdev) if (ret < 0) goto error; - if (!omap4iss_get(iss)) + if (!omap4iss_get(iss)) { + ret = -EINVAL; goto error; + } ret = iss_reset(iss); if (ret < 0) diff --git a/drivers/staging/rtl8192u/r8192U_core.c b/drivers/staging/rtl8192u/r8192U_core.c index 87244a2089763..cc12e6c36fed9 100644 --- a/drivers/staging/rtl8192u/r8192U_core.c +++ b/drivers/staging/rtl8192u/r8192U_core.c @@ -3379,7 +3379,7 @@ static void rtl819x_update_rxcounts(struct r8192_priv *priv, u32 *TotalRxBcnNum, u32 *TotalRxDataNum) { u16 SlotIndex; - u8 i; + u16 i; *TotalRxBcnNum = 0; *TotalRxDataNum = 0; diff --git a/drivers/target/target_core_pscsi.c b/drivers/target/target_core_pscsi.c index 02c4e3beb2640..1b52cd4d793f5 100644 --- a/drivers/target/target_core_pscsi.c +++ b/drivers/target/target_core_pscsi.c @@ -633,8 +633,9 @@ static void pscsi_complete_cmd(struct se_cmd *cmd, u8 scsi_status, unsigned char *buf; buf = transport_kmap_data_sg(cmd); - if (!buf) + if (!buf) { ; /* XXX: TCM_LOGICAL_UNIT_COMMUNICATION_FAILURE */ + } if (cdb[0] == MODE_SENSE_10) { if (!(buf[3] & 0x80)) diff --git a/drivers/target/target_core_user.c b/drivers/target/target_core_user.c index 0219b5a865bee..dd73073755047 100644 --- a/drivers/target/target_core_user.c +++ b/drivers/target/target_core_user.c @@ -1216,7 +1216,7 @@ static void tcmu_set_next_deadline(struct list_head *queue, del_timer(timer); } -static unsigned int tcmu_handle_completions(struct tcmu_dev *udev) +static bool tcmu_handle_completions(struct tcmu_dev *udev) { struct tcmu_mailbox *mb; struct tcmu_cmd *cmd; @@ -1256,7 +1256,7 @@ static unsigned int tcmu_handle_completions(struct tcmu_dev *udev) pr_err("cmd_id %u not found, ring is broken\n", entry->hdr.cmd_id); set_bit(TCMU_DEV_BIT_BROKEN, &udev->flags); - break; + return false; } tcmu_handle_completion(cmd, entry); diff --git a/drivers/tee/optee/core.c b/drivers/tee/optee/core.c index 2f254f957b0af..1d71fcb13dba6 100644 --- a/drivers/tee/optee/core.c +++ b/drivers/tee/optee/core.c @@ -87,16 +87,6 @@ int optee_from_msg_param(struct tee_param *params, size_t num_params, return rc; p->u.memref.shm_offs = mp->u.tmem.buf_ptr - pa; p->u.memref.shm = shm; - - /* Check that the memref is covered by the shm object */ - if (p->u.memref.size) { - size_t o = p->u.memref.shm_offs + - p->u.memref.size - 1; - - rc = tee_shm_get_pa(shm, o, NULL); - if (rc) - return rc; - } break; case OPTEE_MSG_ATTR_TYPE_RMEM_INPUT: case OPTEE_MSG_ATTR_TYPE_RMEM_OUTPUT: diff --git a/drivers/thermal/fair_share.c b/drivers/thermal/fair_share.c index d3469fbc52072..26d7387f58349 100644 --- a/drivers/thermal/fair_share.c +++ b/drivers/thermal/fair_share.c @@ -94,6 +94,8 @@ static int fair_share_throttle(struct thermal_zone_device *tz, int trip) int total_instance = 0; int cur_trip_level = get_trip_level(tz); + mutex_lock(&tz->lock); + list_for_each_entry(instance, &tz->thermal_instances, tz_node) { if (instance->trip != trip) continue; @@ -122,6 +124,8 @@ static int fair_share_throttle(struct thermal_zone_device *tz, int trip) mutex_unlock(&instance->cdev->lock); thermal_cdev_update(cdev); } + + mutex_unlock(&tz->lock); return 0; } diff --git a/drivers/tty/serial/stm32-usart.c b/drivers/tty/serial/stm32-usart.c index bce4ac1787add..50073ead5881b 100644 --- a/drivers/tty/serial/stm32-usart.c +++ b/drivers/tty/serial/stm32-usart.c @@ -472,7 +472,10 @@ static unsigned int stm32_tx_empty(struct uart_port *port) struct stm32_port *stm32_port = to_stm32_port(port); struct stm32_usart_offsets *ofs = &stm32_port->info->ofs; - return readl_relaxed(port->membase + ofs->isr) & USART_SR_TXE; + if (readl_relaxed(port->membase + ofs->isr) & USART_SR_TC) + return TIOCSER_TEMT; + + return 0; } static void stm32_set_mctrl(struct uart_port *port, unsigned int mctrl) @@ -637,8 +640,9 @@ static void stm32_set_termios(struct uart_port *port, struct ktermios *termios, unsigned int baud, bits; u32 usartdiv, mantissa, fraction, oversampling; tcflag_t cflag = termios->c_cflag; - u32 cr1, cr2, cr3; + u32 cr1, cr2, cr3, isr; unsigned long flags; + int ret; if (!stm32_port->hw_flow_control) cflag &= ~CRTSCTS; @@ -647,6 +651,15 @@ static void stm32_set_termios(struct uart_port *port, struct ktermios *termios, spin_lock_irqsave(&port->lock, flags); + ret = readl_relaxed_poll_timeout_atomic(port->membase + ofs->isr, + isr, + (isr & USART_SR_TC), + 10, 100000); + + /* Send the TC error message only when ISR_TC is not set. */ + if (ret) + dev_err(port->dev, "Transmission is not complete\n"); + /* Stop serial port and reset value */ writel_relaxed(0, port->membase + ofs->cr1); diff --git a/drivers/tty/serial/stm32-usart.h b/drivers/tty/serial/stm32-usart.h index 30d2433e27c3c..00daee7f83ee2 100644 --- a/drivers/tty/serial/stm32-usart.h +++ b/drivers/tty/serial/stm32-usart.h @@ -123,9 +123,6 @@ struct stm32_usart_info stm32h7_info = { /* Dummy bits */ #define USART_SR_DUMMY_RX BIT(16) -/* USART_ICR (F7) */ -#define USART_CR_TC BIT(6) - /* USART_DR */ #define USART_DR_MASK GENMASK(8, 0) diff --git a/drivers/tty/tty_io.c b/drivers/tty/tty_io.c index ff6a360eef1ed..9e9343adc2b46 100644 --- a/drivers/tty/tty_io.c +++ b/drivers/tty/tty_io.c @@ -2432,14 +2432,14 @@ out: * @p: pointer to result * * Obtain the modem status bits from the tty driver if the feature - * is supported. Return -EINVAL if it is not available. + * is supported. Return -ENOTTY if it is not available. * * Locking: none (up to the driver) */ static int tty_tiocmget(struct tty_struct *tty, int __user *p) { - int retval = -EINVAL; + int retval = -ENOTTY; if (tty->ops->tiocmget) { retval = tty->ops->tiocmget(tty); @@ -2457,7 +2457,7 @@ static int tty_tiocmget(struct tty_struct *tty, int __user *p) * @p: pointer to desired bits * * Set the modem status bits from the tty driver if the feature - * is supported. Return -EINVAL if it is not available. + * is supported. Return -ENOTTY if it is not available. * * Locking: none (up to the driver) */ @@ -2469,7 +2469,7 @@ static int tty_tiocmset(struct tty_struct *tty, unsigned int cmd, unsigned int set, clear, val; if (tty->ops->tiocmset == NULL) - return -EINVAL; + return -ENOTTY; retval = get_user(val, p); if (retval) diff --git a/drivers/tty/vt/vt.c b/drivers/tty/vt/vt.c index 13ea0579f104c..1fad4978a3b41 100644 --- a/drivers/tty/vt/vt.c +++ b/drivers/tty/vt/vt.c @@ -1380,6 +1380,7 @@ struct vc_data *vc_deallocate(unsigned int currcons) atomic_notifier_call_chain(&vt_notifier_list, VT_DEALLOCATE, ¶m); vcs_remove_sysfs(currcons); visual_deinit(vc); + con_free_unimap(vc); put_pid(vc->vt_pid); vc_uniscr_set(vc, NULL); kfree(vc->vc_screenbuf); diff --git a/drivers/usb/class/cdc-acm.c b/drivers/usb/class/cdc-acm.c index 7f4f21ba8efcf..738de8c9c354b 100644 --- a/drivers/usb/class/cdc-acm.c +++ b/drivers/usb/class/cdc-acm.c @@ -987,8 +987,6 @@ static int set_serial_info(struct acm *acm, if ((new_serial.close_delay != old_close_delay) || (new_serial.closing_wait != old_closing_wait)) retval = -EPERM; - else - retval = -EOPNOTSUPP; } else { acm->port.close_delay = close_delay; acm->port.closing_wait = closing_wait; diff --git a/drivers/usb/class/cdc-wdm.c b/drivers/usb/class/cdc-wdm.c index ae69635bb1fb5..48e775fff16d6 100644 --- a/drivers/usb/class/cdc-wdm.c +++ b/drivers/usb/class/cdc-wdm.c @@ -321,12 +321,23 @@ exit: } -static void kill_urbs(struct wdm_device *desc) +static void poison_urbs(struct wdm_device *desc) { /* the order here is essential */ - usb_kill_urb(desc->command); - usb_kill_urb(desc->validity); - usb_kill_urb(desc->response); + usb_poison_urb(desc->command); + usb_poison_urb(desc->validity); + usb_poison_urb(desc->response); +} + +static void unpoison_urbs(struct wdm_device *desc) +{ + /* + * the order here is not essential + * it is symmetrical just to be nice + */ + usb_unpoison_urb(desc->response); + usb_unpoison_urb(desc->validity); + usb_unpoison_urb(desc->command); } static void free_urbs(struct wdm_device *desc) @@ -741,11 +752,12 @@ static int wdm_release(struct inode *inode, struct file *file) if (!desc->count) { if (!test_bit(WDM_DISCONNECTING, &desc->flags)) { dev_dbg(&desc->intf->dev, "wdm_release: cleanup\n"); - kill_urbs(desc); + poison_urbs(desc); spin_lock_irq(&desc->iuspin); desc->resp_count = 0; spin_unlock_irq(&desc->iuspin); desc->manage_power(desc->intf, 0); + unpoison_urbs(desc); } else { /* must avoid dev_printk here as desc->intf is invalid */ pr_debug(KBUILD_MODNAME " %s: device gone - cleaning up\n", __func__); @@ -1036,9 +1048,9 @@ static void wdm_disconnect(struct usb_interface *intf) wake_up_all(&desc->wait); mutex_lock(&desc->rlock); mutex_lock(&desc->wlock); + poison_urbs(desc); cancel_work_sync(&desc->rxwork); cancel_work_sync(&desc->service_outs_intr); - kill_urbs(desc); mutex_unlock(&desc->wlock); mutex_unlock(&desc->rlock); @@ -1079,9 +1091,10 @@ static int wdm_suspend(struct usb_interface *intf, pm_message_t message) set_bit(WDM_SUSPENDING, &desc->flags); spin_unlock_irq(&desc->iuspin); /* callback submits work - order is essential */ - kill_urbs(desc); + poison_urbs(desc); cancel_work_sync(&desc->rxwork); cancel_work_sync(&desc->service_outs_intr); + unpoison_urbs(desc); } if (!PMSG_IS_AUTO(message)) { mutex_unlock(&desc->wlock); @@ -1139,7 +1152,7 @@ static int wdm_pre_reset(struct usb_interface *intf) wake_up_all(&desc->wait); mutex_lock(&desc->rlock); mutex_lock(&desc->wlock); - kill_urbs(desc); + poison_urbs(desc); cancel_work_sync(&desc->rxwork); cancel_work_sync(&desc->service_outs_intr); return 0; @@ -1150,6 +1163,7 @@ static int wdm_post_reset(struct usb_interface *intf) struct wdm_device *desc = wdm_find_device(intf); int rv; + unpoison_urbs(desc); clear_bit(WDM_OVERFLOW, &desc->flags); clear_bit(WDM_RESETTING, &desc->flags); rv = recover_from_urb_loss(desc); diff --git a/drivers/usb/core/hub.c b/drivers/usb/core/hub.c index fa28f23a4a336..0ddc2e30065f5 100644 --- a/drivers/usb/core/hub.c +++ b/drivers/usb/core/hub.c @@ -3539,9 +3539,6 @@ int usb_port_resume(struct usb_device *udev, pm_message_t msg) * sequence. */ status = hub_port_status(hub, port1, &portstatus, &portchange); - - /* TRSMRCY = 10 msec */ - msleep(10); } SuspendCleared: @@ -3556,6 +3553,9 @@ int usb_port_resume(struct usb_device *udev, pm_message_t msg) usb_clear_port_feature(hub->hdev, port1, USB_PORT_FEAT_C_SUSPEND); } + + /* TRSMRCY = 10 msec */ + msleep(10); } if (udev->persist_enabled) diff --git a/drivers/usb/dwc2/core.h b/drivers/usb/dwc2/core.h index cc9c93affa148..828803b672aa5 100644 --- a/drivers/usb/dwc2/core.h +++ b/drivers/usb/dwc2/core.h @@ -112,6 +112,7 @@ struct dwc2_hsotg_req; * @debugfs: File entry for debugfs file for this endpoint. * @dir_in: Set to true if this endpoint is of the IN direction, which * means that it is sending data to the Host. + * @map_dir: Set to the value of dir_in when the DMA buffer is mapped. * @index: The index for the endpoint registers. * @mc: Multi Count - number of transactions per microframe * @interval: Interval for periodic endpoints, in frames or microframes. @@ -161,6 +162,7 @@ struct dwc2_hsotg_ep { unsigned short fifo_index; unsigned char dir_in; + unsigned char map_dir; unsigned char index; unsigned char mc; u16 interval; diff --git a/drivers/usb/dwc2/core_intr.c b/drivers/usb/dwc2/core_intr.c index b23ce535c12e1..af26a8a20e0bc 100644 --- a/drivers/usb/dwc2/core_intr.c +++ b/drivers/usb/dwc2/core_intr.c @@ -312,6 +312,7 @@ static void dwc2_handle_conn_id_status_change_intr(struct dwc2_hsotg *hsotg) static void dwc2_handle_session_req_intr(struct dwc2_hsotg *hsotg) { int ret; + u32 hprt0; /* Clear interrupt */ dwc2_writel(hsotg, GINTSTS_SESSREQINT, GINTSTS); @@ -332,6 +333,13 @@ static void dwc2_handle_session_req_intr(struct dwc2_hsotg *hsotg) * established */ dwc2_hsotg_disconnect(hsotg); + } else { + /* Turn on the port power bit. */ + hprt0 = dwc2_read_hprt0(hsotg); + hprt0 |= HPRT0_PWR; + dwc2_writel(hsotg, hprt0, HPRT0); + /* Connect hcd after port power is set. */ + dwc2_hcd_connect(hsotg); } } @@ -645,6 +653,71 @@ static u32 dwc2_read_common_intr(struct dwc2_hsotg *hsotg) return 0; } +/** + * dwc_handle_gpwrdn_disc_det() - Handles the gpwrdn disconnect detect. + * Exits hibernation without restoring registers. + * + * @hsotg: Programming view of DWC_otg controller + * @gpwrdn: GPWRDN register + */ +static inline void dwc_handle_gpwrdn_disc_det(struct dwc2_hsotg *hsotg, + u32 gpwrdn) +{ + u32 gpwrdn_tmp; + + /* Switch-on voltage to the core */ + gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); + gpwrdn_tmp &= ~GPWRDN_PWRDNSWTCH; + dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); + udelay(5); + + /* Reset core */ + gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); + gpwrdn_tmp &= ~GPWRDN_PWRDNRSTN; + dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); + udelay(5); + + /* Disable Power Down Clamp */ + gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); + gpwrdn_tmp &= ~GPWRDN_PWRDNCLMP; + dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); + udelay(5); + + /* Deassert reset core */ + gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); + gpwrdn_tmp |= GPWRDN_PWRDNRSTN; + dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); + udelay(5); + + /* Disable PMU interrupt */ + gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); + gpwrdn_tmp &= ~GPWRDN_PMUINTSEL; + dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); + + /* De-assert Wakeup Logic */ + gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); + gpwrdn_tmp &= ~GPWRDN_PMUACTV; + dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); + + hsotg->hibernated = 0; + hsotg->bus_suspended = 0; + + if (gpwrdn & GPWRDN_IDSTS) { + hsotg->op_state = OTG_STATE_B_PERIPHERAL; + dwc2_core_init(hsotg, false); + dwc2_enable_global_interrupts(hsotg); + dwc2_hsotg_core_init_disconnected(hsotg, false); + dwc2_hsotg_core_connect(hsotg); + } else { + hsotg->op_state = OTG_STATE_A_HOST; + + /* Initialize the Core for Host mode */ + dwc2_core_init(hsotg, false); + dwc2_enable_global_interrupts(hsotg); + dwc2_hcd_start(hsotg); + } +} + /* * GPWRDN interrupt handler. * @@ -666,64 +739,14 @@ static void dwc2_handle_gpwrdn_intr(struct dwc2_hsotg *hsotg) if ((gpwrdn & GPWRDN_DISCONN_DET) && (gpwrdn & GPWRDN_DISCONN_DET_MSK) && !linestate) { - u32 gpwrdn_tmp; - dev_dbg(hsotg->dev, "%s: GPWRDN_DISCONN_DET\n", __func__); - - /* Switch-on voltage to the core */ - gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); - gpwrdn_tmp &= ~GPWRDN_PWRDNSWTCH; - dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); - udelay(10); - - /* Reset core */ - gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); - gpwrdn_tmp &= ~GPWRDN_PWRDNRSTN; - dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); - udelay(10); - - /* Disable Power Down Clamp */ - gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); - gpwrdn_tmp &= ~GPWRDN_PWRDNCLMP; - dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); - udelay(10); - - /* Deassert reset core */ - gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); - gpwrdn_tmp |= GPWRDN_PWRDNRSTN; - dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); - udelay(10); - - /* Disable PMU interrupt */ - gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); - gpwrdn_tmp &= ~GPWRDN_PMUINTSEL; - dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); - - /* De-assert Wakeup Logic */ - gpwrdn_tmp = dwc2_readl(hsotg, GPWRDN); - gpwrdn_tmp &= ~GPWRDN_PMUACTV; - dwc2_writel(hsotg, gpwrdn_tmp, GPWRDN); - - hsotg->hibernated = 0; - - if (gpwrdn & GPWRDN_IDSTS) { - hsotg->op_state = OTG_STATE_B_PERIPHERAL; - dwc2_core_init(hsotg, false); - dwc2_enable_global_interrupts(hsotg); - dwc2_hsotg_core_init_disconnected(hsotg, false); - dwc2_hsotg_core_connect(hsotg); - } else { - hsotg->op_state = OTG_STATE_A_HOST; - - /* Initialize the Core for Host mode */ - dwc2_core_init(hsotg, false); - dwc2_enable_global_interrupts(hsotg); - dwc2_hcd_start(hsotg); - } - } - - if ((gpwrdn & GPWRDN_LNSTSCHG) && - (gpwrdn & GPWRDN_LNSTSCHG_MSK) && linestate) { + /* + * Call disconnect detect function to exit from + * hibernation + */ + dwc_handle_gpwrdn_disc_det(hsotg, gpwrdn); + } else if ((gpwrdn & GPWRDN_LNSTSCHG) && + (gpwrdn & GPWRDN_LNSTSCHG_MSK) && linestate) { dev_dbg(hsotg->dev, "%s: GPWRDN_LNSTSCHG\n", __func__); if (hsotg->hw_params.hibernation && hsotg->hibernated) { @@ -734,24 +757,21 @@ static void dwc2_handle_gpwrdn_intr(struct dwc2_hsotg *hsotg) dwc2_exit_hibernation(hsotg, 1, 0, 1); } } - } - if ((gpwrdn & GPWRDN_RST_DET) && (gpwrdn & GPWRDN_RST_DET_MSK)) { + } else if ((gpwrdn & GPWRDN_RST_DET) && + (gpwrdn & GPWRDN_RST_DET_MSK)) { dev_dbg(hsotg->dev, "%s: GPWRDN_RST_DET\n", __func__); if (!linestate && (gpwrdn & GPWRDN_BSESSVLD)) dwc2_exit_hibernation(hsotg, 0, 1, 0); - } - if ((gpwrdn & GPWRDN_STS_CHGINT) && - (gpwrdn & GPWRDN_STS_CHGINT_MSK) && linestate) { + } else if ((gpwrdn & GPWRDN_STS_CHGINT) && + (gpwrdn & GPWRDN_STS_CHGINT_MSK)) { dev_dbg(hsotg->dev, "%s: GPWRDN_STS_CHGINT\n", __func__); - if (hsotg->hw_params.hibernation && - hsotg->hibernated) { - if (gpwrdn & GPWRDN_IDSTS) { - dwc2_exit_hibernation(hsotg, 0, 0, 0); - call_gadget(hsotg, resume); - } else { - dwc2_exit_hibernation(hsotg, 1, 0, 1); - } - } + /* + * As GPWRDN_STS_CHGINT exit from hibernation flow is + * the same as in GPWRDN_DISCONN_DET flow. Call + * disconnect detect helper function to exit from + * hibernation. + */ + dwc_handle_gpwrdn_disc_det(hsotg, gpwrdn); } } diff --git a/drivers/usb/dwc2/gadget.c b/drivers/usb/dwc2/gadget.c index 42f66718bc184..d0edb7e453c07 100644 --- a/drivers/usb/dwc2/gadget.c +++ b/drivers/usb/dwc2/gadget.c @@ -380,7 +380,7 @@ static void dwc2_hsotg_unmap_dma(struct dwc2_hsotg *hsotg, { struct usb_request *req = &hs_req->req; - usb_gadget_unmap_request(&hsotg->gadget, req, hs_ep->dir_in); + usb_gadget_unmap_request(&hsotg->gadget, req, hs_ep->map_dir); } /* @@ -1163,6 +1163,7 @@ static int dwc2_hsotg_map_dma(struct dwc2_hsotg *hsotg, { int ret; + hs_ep->map_dir = hs_ep->dir_in; ret = usb_gadget_map_request(&hsotg->gadget, req, hs_ep->dir_in); if (ret) goto dma_error; diff --git a/drivers/usb/dwc2/hcd.c b/drivers/usb/dwc2/hcd.c index 91686e1b24d97..58e53e3d905be 100644 --- a/drivers/usb/dwc2/hcd.c +++ b/drivers/usb/dwc2/hcd.c @@ -5741,7 +5741,15 @@ int dwc2_host_exit_hibernation(struct dwc2_hsotg *hsotg, int rem_wakeup, return ret; } - dwc2_hcd_rem_wakeup(hsotg); + if (rem_wakeup) { + dwc2_hcd_rem_wakeup(hsotg); + /* + * Change "port_connect_status_change" flag to re-enumerate, + * because after exit from hibernation port connection status + * is not detected. + */ + hsotg->flags.b.port_connect_status_change = 1; + } hsotg->hibernated = 0; hsotg->bus_suspended = 0; diff --git a/drivers/usb/dwc3/dwc3-omap.c b/drivers/usb/dwc3/dwc3-omap.c index ed8b865176758..0dfb710f48b5e 100644 --- a/drivers/usb/dwc3/dwc3-omap.c +++ b/drivers/usb/dwc3/dwc3-omap.c @@ -432,8 +432,13 @@ static int dwc3_omap_extcon_register(struct dwc3_omap *omap) if (extcon_get_state(edev, EXTCON_USB) == true) dwc3_omap_set_mailbox(omap, OMAP_DWC3_VBUS_VALID); + else + dwc3_omap_set_mailbox(omap, OMAP_DWC3_VBUS_OFF); + if (extcon_get_state(edev, EXTCON_USB_HOST) == true) dwc3_omap_set_mailbox(omap, OMAP_DWC3_ID_GROUND); + else + dwc3_omap_set_mailbox(omap, OMAP_DWC3_ID_FLOAT); omap->edev = edev; } diff --git a/drivers/usb/dwc3/dwc3-pci.c b/drivers/usb/dwc3/dwc3-pci.c index 389ec4c689c44..bf40a2f36e976 100644 --- a/drivers/usb/dwc3/dwc3-pci.c +++ b/drivers/usb/dwc3/dwc3-pci.c @@ -133,6 +133,7 @@ static const struct property_entry dwc3_pci_amd_properties[] = { PROPERTY_ENTRY_BOOL("snps,disable_scramble_quirk"), PROPERTY_ENTRY_BOOL("snps,dis_u3_susphy_quirk"), PROPERTY_ENTRY_BOOL("snps,dis_u2_susphy_quirk"), + PROPERTY_ENTRY_BOOL("snps,usb2-gadget-lpm-disable"), PROPERTY_ENTRY_BOOL("linux,sysdev_is_parent"), {} }; diff --git a/drivers/usb/dwc3/gadget.c b/drivers/usb/dwc3/gadget.c index a0806dca3de9d..8ce13f5e83c73 100644 --- a/drivers/usb/dwc3/gadget.c +++ b/drivers/usb/dwc3/gadget.c @@ -304,13 +304,12 @@ int dwc3_send_gadget_ep_cmd(struct dwc3_ep *dep, unsigned cmd, } if (DWC3_DEPCMD_CMD(cmd) == DWC3_DEPCMD_STARTTRANSFER) { - int needs_wakeup; + int link_state; - needs_wakeup = (dwc->link_state == DWC3_LINK_STATE_U1 || - dwc->link_state == DWC3_LINK_STATE_U2 || - dwc->link_state == DWC3_LINK_STATE_U3); - - if (unlikely(needs_wakeup)) { + link_state = dwc3_gadget_get_link_state(dwc); + if (link_state == DWC3_LINK_STATE_U1 || + link_state == DWC3_LINK_STATE_U2 || + link_state == DWC3_LINK_STATE_U3) { ret = __dwc3_gadget_wakeup(dwc); dev_WARN_ONCE(dwc->dev, ret, "wakeup failed --> %d\n", ret); @@ -1414,7 +1413,9 @@ static int __dwc3_gadget_ep_queue(struct dwc3_ep *dep, struct dwc3_request *req) } } - return __dwc3_gadget_kick_transfer(dep); + __dwc3_gadget_kick_transfer(dep); + + return 0; } static int dwc3_gadget_ep_queue(struct usb_ep *ep, struct usb_request *request, @@ -1674,6 +1675,8 @@ static int __dwc3_gadget_wakeup(struct dwc3 *dwc) case DWC3_LINK_STATE_RESET: case DWC3_LINK_STATE_RX_DET: /* in HS, means Early Suspend */ case DWC3_LINK_STATE_U3: /* in HS, means SUSPEND */ + case DWC3_LINK_STATE_U2: /* in HS, means Sleep (L1) */ + case DWC3_LINK_STATE_U1: case DWC3_LINK_STATE_RESUME: break; default: @@ -2717,6 +2720,15 @@ static void dwc3_gadget_reset_interrupt(struct dwc3 *dwc) dwc->connected = true; + /* + * Ideally, dwc3_reset_gadget() would trigger the function + * drivers to stop any active transfers through ep disable. + * However, for functions which defer ep disable, such as mass + * storage, we will need to rely on the call to stop active + * transfers here, and avoid allowing of request queuing. + */ + dwc->connected = false; + /* * WORKAROUND: DWC3 revisions <1.88a have an issue which * would cause a missing Disconnect Event if there's a diff --git a/drivers/usb/gadget/config.c b/drivers/usb/gadget/config.c index 2d115353424c2..8bb25773b61e9 100644 --- a/drivers/usb/gadget/config.c +++ b/drivers/usb/gadget/config.c @@ -194,9 +194,13 @@ EXPORT_SYMBOL_GPL(usb_assign_descriptors); void usb_free_all_descriptors(struct usb_function *f) { usb_free_descriptors(f->fs_descriptors); + f->fs_descriptors = NULL; usb_free_descriptors(f->hs_descriptors); + f->hs_descriptors = NULL; usb_free_descriptors(f->ss_descriptors); + f->ss_descriptors = NULL; usb_free_descriptors(f->ssp_descriptors); + f->ssp_descriptors = NULL; } EXPORT_SYMBOL_GPL(usb_free_all_descriptors); diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c index 5c1846d1372ec..dcb432860d062 100644 --- a/drivers/usb/gadget/function/f_fs.c +++ b/drivers/usb/gadget/function/f_fs.c @@ -2553,6 +2553,7 @@ static int __ffs_data_got_strings(struct ffs_data *ffs, do { /* lang_count > 0 so we can use do-while */ unsigned needed = needed_count; + u32 str_per_lang = str_count; if (unlikely(len < 3)) goto error_free; @@ -2588,7 +2589,7 @@ static int __ffs_data_got_strings(struct ffs_data *ffs, data += length + 1; len -= length + 1; - } while (--str_count); + } while (--str_per_lang); s->id = 0; /* terminator */ s->s = NULL; diff --git a/drivers/usb/gadget/function/f_uac1.c b/drivers/usb/gadget/function/f_uac1.c index a215c836eba4b..41e7b29f58dfe 100644 --- a/drivers/usb/gadget/function/f_uac1.c +++ b/drivers/usb/gadget/function/f_uac1.c @@ -19,6 +19,9 @@ #include "u_audio.h" #include "u_uac1.h" +/* UAC1 spec: 3.7.2.3 Audio Channel Cluster Format */ +#define UAC1_CHANNEL_MASK 0x0FFF + struct f_uac1 { struct g_audio g_audio; u8 ac_intf, as_in_intf, as_out_intf; @@ -30,6 +33,11 @@ static inline struct f_uac1 *func_to_uac1(struct usb_function *f) return container_of(f, struct f_uac1, g_audio.func); } +static inline struct f_uac1_opts *g_audio_to_uac1_opts(struct g_audio *audio) +{ + return container_of(audio->func.fi, struct f_uac1_opts, func_inst); +} + /* * DESCRIPTORS ... most are static, but strings and full * configuration descriptors are built on demand. @@ -505,11 +513,42 @@ static void f_audio_disable(struct usb_function *f) /*-------------------------------------------------------------------------*/ +static int f_audio_validate_opts(struct g_audio *audio, struct device *dev) +{ + struct f_uac1_opts *opts = g_audio_to_uac1_opts(audio); + + if (!opts->p_chmask && !opts->c_chmask) { + dev_err(dev, "Error: no playback and capture channels\n"); + return -EINVAL; + } else if (opts->p_chmask & ~UAC1_CHANNEL_MASK) { + dev_err(dev, "Error: unsupported playback channels mask\n"); + return -EINVAL; + } else if (opts->c_chmask & ~UAC1_CHANNEL_MASK) { + dev_err(dev, "Error: unsupported capture channels mask\n"); + return -EINVAL; + } else if ((opts->p_ssize < 1) || (opts->p_ssize > 4)) { + dev_err(dev, "Error: incorrect playback sample size\n"); + return -EINVAL; + } else if ((opts->c_ssize < 1) || (opts->c_ssize > 4)) { + dev_err(dev, "Error: incorrect capture sample size\n"); + return -EINVAL; + } else if (!opts->p_srate) { + dev_err(dev, "Error: incorrect playback sampling rate\n"); + return -EINVAL; + } else if (!opts->c_srate) { + dev_err(dev, "Error: incorrect capture sampling rate\n"); + return -EINVAL; + } + + return 0; +} + /* audio function driver setup/binding */ static int f_audio_bind(struct usb_configuration *c, struct usb_function *f) { struct usb_composite_dev *cdev = c->cdev; struct usb_gadget *gadget = cdev->gadget; + struct device *dev = &gadget->dev; struct f_uac1 *uac1 = func_to_uac1(f); struct g_audio *audio = func_to_g_audio(f); struct f_uac1_opts *audio_opts; @@ -519,6 +558,10 @@ static int f_audio_bind(struct usb_configuration *c, struct usb_function *f) int rate; int status; + status = f_audio_validate_opts(audio, dev); + if (status) + return status; + audio_opts = container_of(f->fi, struct f_uac1_opts, func_inst); us = usb_gstrings_attach(cdev, uac1_strings, ARRAY_SIZE(strings_uac1)); diff --git a/drivers/usb/gadget/function/f_uvc.c b/drivers/usb/gadget/function/f_uvc.c index d8ce7868fe225..169e73ed128c8 100644 --- a/drivers/usb/gadget/function/f_uvc.c +++ b/drivers/usb/gadget/function/f_uvc.c @@ -645,7 +645,12 @@ uvc_function_bind(struct usb_configuration *c, struct usb_function *f) uvc_hs_streaming_ep.wMaxPacketSize = cpu_to_le16(max_packet_size | ((max_packet_mult - 1) << 11)); - uvc_hs_streaming_ep.bInterval = opts->streaming_interval; + + /* A high-bandwidth endpoint must specify a bInterval value of 1 */ + if (max_packet_mult > 1) + uvc_hs_streaming_ep.bInterval = 1; + else + uvc_hs_streaming_ep.bInterval = opts->streaming_interval; uvc_ss_streaming_ep.wMaxPacketSize = cpu_to_le16(max_packet_size); uvc_ss_streaming_ep.bInterval = opts->streaming_interval; diff --git a/drivers/usb/gadget/udc/aspeed-vhub/core.c b/drivers/usb/gadget/udc/aspeed-vhub/core.c index db3628be38c07..902e61be4d642 100644 --- a/drivers/usb/gadget/udc/aspeed-vhub/core.c +++ b/drivers/usb/gadget/udc/aspeed-vhub/core.c @@ -36,6 +36,7 @@ void ast_vhub_done(struct ast_vhub_ep *ep, struct ast_vhub_req *req, int status) { bool internal = req->internal; + struct ast_vhub *vhub = ep->vhub; EPVDBG(ep, "completing request @%p, status %d\n", req, status); @@ -46,7 +47,7 @@ void ast_vhub_done(struct ast_vhub_ep *ep, struct ast_vhub_req *req, if (req->req.dma) { if (!WARN_ON(!ep->dev)) - usb_gadget_unmap_request(&ep->dev->gadget, + usb_gadget_unmap_request_by_dev(&vhub->pdev->dev, &req->req, ep->epn.is_in); req->req.dma = 0; } diff --git a/drivers/usb/gadget/udc/aspeed-vhub/epn.c b/drivers/usb/gadget/udc/aspeed-vhub/epn.c index ae853cf369662..931f540a747e9 100644 --- a/drivers/usb/gadget/udc/aspeed-vhub/epn.c +++ b/drivers/usb/gadget/udc/aspeed-vhub/epn.c @@ -376,7 +376,7 @@ static int ast_vhub_epn_queue(struct usb_ep* u_ep, struct usb_request *u_req, if (ep->epn.desc_mode || ((((unsigned long)u_req->buf & 7) == 0) && (ep->epn.is_in || !(u_req->length & (u_ep->maxpacket - 1))))) { - rc = usb_gadget_map_request(&ep->dev->gadget, u_req, + rc = usb_gadget_map_request_by_dev(&vhub->pdev->dev, u_req, ep->epn.is_in); if (rc) { dev_warn(&vhub->pdev->dev, diff --git a/drivers/usb/gadget/udc/dummy_hcd.c b/drivers/usb/gadget/udc/dummy_hcd.c index fdbce8529dbb4..d25d25da6875d 100644 --- a/drivers/usb/gadget/udc/dummy_hcd.c +++ b/drivers/usb/gadget/udc/dummy_hcd.c @@ -914,6 +914,21 @@ static int dummy_pullup(struct usb_gadget *_gadget, int value) spin_lock_irqsave(&dum->lock, flags); dum->pullup = (value != 0); set_link_state(dum_hcd); + if (value == 0) { + /* + * Emulate synchronize_irq(): wait for callbacks to finish. + * This seems to be the best place to emulate the call to + * synchronize_irq() that's in usb_gadget_remove_driver(). + * Doing it in dummy_udc_stop() would be too late since it + * is called after the unbind callback and unbind shouldn't + * be invoked until all the other callbacks are finished. + */ + while (dum->callback_usage > 0) { + spin_unlock_irqrestore(&dum->lock, flags); + usleep_range(1000, 2000); + spin_lock_irqsave(&dum->lock, flags); + } + } spin_unlock_irqrestore(&dum->lock, flags); usb_hcd_poll_rh_status(dummy_hcd_to_hcd(dum_hcd)); @@ -1015,14 +1030,6 @@ static int dummy_udc_stop(struct usb_gadget *g) spin_lock_irq(&dum->lock); dum->ints_enabled = 0; stop_activity(dum); - - /* emulate synchronize_irq(): wait for callbacks to finish */ - while (dum->callback_usage > 0) { - spin_unlock_irq(&dum->lock); - usleep_range(1000, 2000); - spin_lock_irq(&dum->lock); - } - dum->driver = NULL; spin_unlock_irq(&dum->lock); diff --git a/drivers/usb/gadget/udc/fotg210-udc.c b/drivers/usb/gadget/udc/fotg210-udc.c index bc6abaea907d8..785822ecc3f1a 100644 --- a/drivers/usb/gadget/udc/fotg210-udc.c +++ b/drivers/usb/gadget/udc/fotg210-udc.c @@ -337,15 +337,16 @@ static void fotg210_start_dma(struct fotg210_ep *ep, } else { buffer = req->req.buf + req->req.actual; length = ioread32(ep->fotg210->reg + - FOTG210_FIBCR(ep->epnum - 1)); - length &= FIBCR_BCFX; + FOTG210_FIBCR(ep->epnum - 1)) & FIBCR_BCFX; + if (length > req->req.length - req->req.actual) + length = req->req.length - req->req.actual; } } else { buffer = req->req.buf + req->req.actual; if (req->req.length - req->req.actual > ep->ep.maxpacket) length = ep->ep.maxpacket; else - length = req->req.length; + length = req->req.length - req->req.actual; } d = dma_map_single(NULL, buffer, length, @@ -382,8 +383,7 @@ static void fotg210_ep0_queue(struct fotg210_ep *ep, } if (ep->dir_in) { /* if IN */ fotg210_start_dma(ep, req); - if ((req->req.length == req->req.actual) || - (req->req.actual < ep->ep.maxpacket)) + if (req->req.length == req->req.actual) fotg210_done(ep, req, 0); } else { /* OUT */ u32 value = ioread32(ep->fotg210->reg + FOTG210_DMISGR0); @@ -824,7 +824,7 @@ static void fotg210_ep0in(struct fotg210_udc *fotg210) if (req->req.length) fotg210_start_dma(ep, req); - if ((req->req.length - req->req.actual) < ep->ep.maxpacket) + if (req->req.actual == req->req.length) fotg210_done(ep, req, 0); } else { fotg210_set_cxdone(fotg210); @@ -853,12 +853,16 @@ static void fotg210_out_fifo_handler(struct fotg210_ep *ep) { struct fotg210_request *req = list_entry(ep->queue.next, struct fotg210_request, queue); + int disgr1 = ioread32(ep->fotg210->reg + FOTG210_DISGR1); fotg210_start_dma(ep, req); - /* finish out transfer */ + /* Complete the request when it's full or a short packet arrived. + * Like other drivers, short_not_ok isn't handled. + */ + if (req->req.length == req->req.actual || - req->req.actual < ep->ep.maxpacket) + (disgr1 & DISGR1_SPK_INT(ep->epnum - 1))) fotg210_done(ep, req, 0); } @@ -1031,6 +1035,12 @@ static void fotg210_init(struct fotg210_udc *fotg210) value &= ~DMCR_GLINT_EN; iowrite32(value, fotg210->reg + FOTG210_DMCR); + /* enable only grp2 irqs we handle */ + iowrite32(~(DISGR2_DMA_ERROR | DISGR2_RX0BYTE_INT | DISGR2_TX0BYTE_INT + | DISGR2_ISO_SEQ_ABORT_INT | DISGR2_ISO_SEQ_ERR_INT + | DISGR2_RESM_INT | DISGR2_SUSP_INT | DISGR2_USBRST_INT), + fotg210->reg + FOTG210_DMISGR2); + /* disable all fifo interrupt */ iowrite32(~(u32)0, fotg210->reg + FOTG210_DMISGR1); diff --git a/drivers/usb/gadget/udc/pch_udc.c b/drivers/usb/gadget/udc/pch_udc.c index 667011c993727..14e99905cbeef 100644 --- a/drivers/usb/gadget/udc/pch_udc.c +++ b/drivers/usb/gadget/udc/pch_udc.c @@ -600,18 +600,22 @@ static void pch_udc_reconnect(struct pch_udc_dev *dev) static inline void pch_udc_vbus_session(struct pch_udc_dev *dev, int is_active) { + unsigned long iflags; + + spin_lock_irqsave(&dev->lock, iflags); if (is_active) { pch_udc_reconnect(dev); dev->vbus_session = 1; } else { if (dev->driver && dev->driver->disconnect) { - spin_lock(&dev->lock); + spin_unlock_irqrestore(&dev->lock, iflags); dev->driver->disconnect(&dev->gadget); - spin_unlock(&dev->lock); + spin_lock_irqsave(&dev->lock, iflags); } pch_udc_set_disconnect(dev); dev->vbus_session = 0; } + spin_unlock_irqrestore(&dev->lock, iflags); } /** @@ -1168,20 +1172,25 @@ static int pch_udc_pcd_selfpowered(struct usb_gadget *gadget, int value) static int pch_udc_pcd_pullup(struct usb_gadget *gadget, int is_on) { struct pch_udc_dev *dev; + unsigned long iflags; if (!gadget) return -EINVAL; + dev = container_of(gadget, struct pch_udc_dev, gadget); + + spin_lock_irqsave(&dev->lock, iflags); if (is_on) { pch_udc_reconnect(dev); } else { if (dev->driver && dev->driver->disconnect) { - spin_lock(&dev->lock); + spin_unlock_irqrestore(&dev->lock, iflags); dev->driver->disconnect(&dev->gadget); - spin_unlock(&dev->lock); + spin_lock_irqsave(&dev->lock, iflags); } pch_udc_set_disconnect(dev); } + spin_unlock_irqrestore(&dev->lock, iflags); return 0; } @@ -1773,7 +1782,7 @@ static struct usb_request *pch_udc_alloc_request(struct usb_ep *usbep, } /* prevent from using desc. - set HOST BUSY */ dma_desc->status |= PCH_UDC_BS_HST_BSY; - dma_desc->dataptr = cpu_to_le32(DMA_ADDR_INVALID); + dma_desc->dataptr = lower_32_bits(DMA_ADDR_INVALID); req->td_data = dma_desc; req->td_data_last = dma_desc; req->chain_len = 1; @@ -2316,6 +2325,21 @@ static void pch_udc_svc_data_out(struct pch_udc_dev *dev, int ep_num) pch_udc_set_dma(dev, DMA_DIR_RX); } +static int pch_udc_gadget_setup(struct pch_udc_dev *dev) + __must_hold(&dev->lock) +{ + int rc; + + /* In some cases we can get an interrupt before driver gets setup */ + if (!dev->driver) + return -ESHUTDOWN; + + spin_unlock(&dev->lock); + rc = dev->driver->setup(&dev->gadget, &dev->setup_data); + spin_lock(&dev->lock); + return rc; +} + /** * pch_udc_svc_control_in() - Handle Control IN endpoint interrupts * @dev: Reference to the device structure @@ -2387,15 +2411,12 @@ static void pch_udc_svc_control_out(struct pch_udc_dev *dev) dev->gadget.ep0 = &dev->ep[UDC_EP0IN_IDX].ep; else /* OUT */ dev->gadget.ep0 = &ep->ep; - spin_lock(&dev->lock); /* If Mass storage Reset */ if ((dev->setup_data.bRequestType == 0x21) && (dev->setup_data.bRequest == 0xFF)) dev->prot_stall = 0; /* call gadget with setup data received */ - setup_supported = dev->driver->setup(&dev->gadget, - &dev->setup_data); - spin_unlock(&dev->lock); + setup_supported = pch_udc_gadget_setup(dev); if (dev->setup_data.bRequestType & USB_DIR_IN) { ep->td_data->status = (ep->td_data->status & @@ -2643,9 +2664,7 @@ static void pch_udc_svc_intf_interrupt(struct pch_udc_dev *dev) dev->ep[i].halted = 0; } dev->stall = 0; - spin_unlock(&dev->lock); - dev->driver->setup(&dev->gadget, &dev->setup_data); - spin_lock(&dev->lock); + pch_udc_gadget_setup(dev); } /** @@ -2680,9 +2699,7 @@ static void pch_udc_svc_cfg_interrupt(struct pch_udc_dev *dev) dev->stall = 0; /* call gadget zero with setup data received */ - spin_unlock(&dev->lock); - dev->driver->setup(&dev->gadget, &dev->setup_data); - spin_lock(&dev->lock); + pch_udc_gadget_setup(dev); } /** @@ -2956,7 +2973,7 @@ static int init_dma_pools(struct pch_udc_dev *dev) dev->dma_addr = dma_map_single(&dev->pdev->dev, ep0out_buf, UDC_EP0OUT_BUFF_SIZE * 4, DMA_FROM_DEVICE); - return 0; + return dma_mapping_error(&dev->pdev->dev, dev->dma_addr); } static int pch_udc_start(struct usb_gadget *g, diff --git a/drivers/usb/gadget/udc/r8a66597-udc.c b/drivers/usb/gadget/udc/r8a66597-udc.c index 11e25a3f4f1fa..a766476fd742e 100644 --- a/drivers/usb/gadget/udc/r8a66597-udc.c +++ b/drivers/usb/gadget/udc/r8a66597-udc.c @@ -1852,6 +1852,8 @@ static int r8a66597_probe(struct platform_device *pdev) return PTR_ERR(reg); ires = platform_get_resource(pdev, IORESOURCE_IRQ, 0); + if (!ires) + return -EINVAL; irq = ires->start; irq_trigger = ires->flags & IRQF_TRIGGER_MASK; diff --git a/drivers/usb/gadget/udc/snps_udc_plat.c b/drivers/usb/gadget/udc/snps_udc_plat.c index 32f1d3e90c264..99805d60a7ab3 100644 --- a/drivers/usb/gadget/udc/snps_udc_plat.c +++ b/drivers/usb/gadget/udc/snps_udc_plat.c @@ -114,8 +114,8 @@ static int udc_plat_probe(struct platform_device *pdev) res = platform_get_resource(pdev, IORESOURCE_MEM, 0); udc->virt_addr = devm_ioremap_resource(dev, res); - if (IS_ERR(udc->regs)) - return PTR_ERR(udc->regs); + if (IS_ERR(udc->virt_addr)) + return PTR_ERR(udc->virt_addr); /* udc csr registers base */ udc->csr = udc->virt_addr + UDC_CSR_ADDR; diff --git a/drivers/usb/host/fotg210-hcd.c b/drivers/usb/host/fotg210-hcd.c index 2d5a72c15069e..226b38274a6ef 100644 --- a/drivers/usb/host/fotg210-hcd.c +++ b/drivers/usb/host/fotg210-hcd.c @@ -5569,7 +5569,7 @@ static int fotg210_hcd_probe(struct platform_device *pdev) struct usb_hcd *hcd; struct resource *res; int irq; - int retval = -ENODEV; + int retval; struct fotg210_hcd *fotg210; if (usb_disabled()) @@ -5589,7 +5589,7 @@ static int fotg210_hcd_probe(struct platform_device *pdev) hcd = usb_create_hcd(&fotg210_fotg210_hc_driver, dev, dev_name(dev)); if (!hcd) { - dev_err(dev, "failed to create hcd with err %d\n", retval); + dev_err(dev, "failed to create hcd\n"); retval = -ENOMEM; goto fail_create_hcd; } diff --git a/drivers/usb/host/sl811-hcd.c b/drivers/usb/host/sl811-hcd.c index 5b061e5999489..6dedefada92b1 100644 --- a/drivers/usb/host/sl811-hcd.c +++ b/drivers/usb/host/sl811-hcd.c @@ -1287,11 +1287,10 @@ sl811h_hub_control( goto error; put_unaligned_le32(sl811->port1, buf); -#ifndef VERBOSE - if (*(u16*)(buf+2)) /* only if wPortChange is interesting */ -#endif - dev_dbg(hcd->self.controller, "GetPortStatus %08x\n", - sl811->port1); + if (__is_defined(VERBOSE) || + *(u16*)(buf+2)) /* only if wPortChange is interesting */ + dev_dbg(hcd->self.controller, "GetPortStatus %08x\n", + sl811->port1); break; case SetPortFeature: if (wIndex != 1 || wLength != 0) diff --git a/drivers/usb/host/xhci-ext-caps.h b/drivers/usb/host/xhci-ext-caps.h index 268328c206816..2208fa6c74109 100644 --- a/drivers/usb/host/xhci-ext-caps.h +++ b/drivers/usb/host/xhci-ext-caps.h @@ -7,8 +7,9 @@ * Author: Sarah Sharp * Some code borrowed from the Linux EHCI driver. */ -/* Up to 16 ms to halt an HC */ -#define XHCI_MAX_HALT_USEC (16*1000) + +/* HC should halt within 16 ms, but use 32 ms as some hosts take longer */ +#define XHCI_MAX_HALT_USEC (32 * 1000) /* HC not running - set to 1 when run/stop bit is cleared. */ #define XHCI_STS_HALT (1<<0) diff --git a/drivers/usb/host/xhci-mem.c b/drivers/usb/host/xhci-mem.c index 9e87c282a7435..2461be2a8748c 100644 --- a/drivers/usb/host/xhci-mem.c +++ b/drivers/usb/host/xhci-mem.c @@ -2134,6 +2134,15 @@ static void xhci_add_in_port(struct xhci_hcd *xhci, unsigned int num_ports, if (major_revision == 0x03) { rhub = &xhci->usb3_rhub; + /* + * Some hosts incorrectly use sub-minor version for minor + * version (i.e. 0x02 instead of 0x20 for bcdUSB 0x320 and 0x01 + * for bcdUSB 0x310). Since there is no USB release with sub + * minor version 0x301 to 0x309, we can assume that they are + * incorrect and fix it here. + */ + if (minor_revision > 0x00 && minor_revision < 0x10) + minor_revision <<= 4; } else if (major_revision <= 0x02) { rhub = &xhci->usb2_rhub; } else { diff --git a/drivers/usb/host/xhci-mtk.c b/drivers/usb/host/xhci-mtk.c index 09d5a789fcd5d..f4b2e766f195b 100644 --- a/drivers/usb/host/xhci-mtk.c +++ b/drivers/usb/host/xhci-mtk.c @@ -395,6 +395,8 @@ static void xhci_mtk_quirks(struct device *dev, struct xhci_hcd *xhci) xhci->quirks |= XHCI_SPURIOUS_SUCCESS; if (mtk->lpm_support) xhci->quirks |= XHCI_LPM_SUPPORT; + if (mtk->u2_lpm_disable) + xhci->quirks |= XHCI_HW_LPM_DISABLE; /* * MTK xHCI 0.96: PSA is 1 by default even if doesn't support stream, @@ -467,6 +469,7 @@ static int xhci_mtk_probe(struct platform_device *pdev) return ret; mtk->lpm_support = of_property_read_bool(node, "usb3-lpm-capable"); + mtk->u2_lpm_disable = of_property_read_bool(node, "usb2-lpm-disable"); /* optional property, ignore the error if it does not exist */ of_property_read_u32(node, "mediatek,u3p-dis-msk", &mtk->u3p_dis_msk); diff --git a/drivers/usb/host/xhci-mtk.h b/drivers/usb/host/xhci-mtk.h index cc59d80b663b4..1601ca9a388e8 100644 --- a/drivers/usb/host/xhci-mtk.h +++ b/drivers/usb/host/xhci-mtk.h @@ -123,6 +123,7 @@ struct xhci_hcd_mtk { struct phy **phys; int num_phys; bool lpm_support; + bool u2_lpm_disable; /* usb remote wakeup */ bool uwk_en; struct regmap *uwk; diff --git a/drivers/usb/host/xhci-pci.c b/drivers/usb/host/xhci-pci.c index 42ff11e3c4dcf..19485c076ba30 100644 --- a/drivers/usb/host/xhci-pci.c +++ b/drivers/usb/host/xhci-pci.c @@ -144,8 +144,10 @@ static void xhci_pci_quirks(struct device *dev, struct xhci_hcd *xhci) (pdev->device == 0x15e0 || pdev->device == 0x15e1)) xhci->quirks |= XHCI_SNPS_BROKEN_SUSPEND; - if (pdev->vendor == PCI_VENDOR_ID_AMD && pdev->device == 0x15e5) + if (pdev->vendor == PCI_VENDOR_ID_AMD && pdev->device == 0x15e5) { xhci->quirks |= XHCI_DISABLE_SPARSE; + xhci->quirks |= XHCI_RESET_ON_RESUME; + } if (pdev->vendor == PCI_VENDOR_ID_AMD) xhci->quirks |= XHCI_TRUST_TX_LENGTH; diff --git a/drivers/usb/host/xhci.c b/drivers/usb/host/xhci.c index 6c508d0313f7f..c4e3760abd5b4 100644 --- a/drivers/usb/host/xhci.c +++ b/drivers/usb/host/xhci.c @@ -227,6 +227,7 @@ static void xhci_zero_64b_regs(struct xhci_hcd *xhci) struct device *dev = xhci_to_hcd(xhci)->self.sysdev; int err, i; u64 val; + u32 intrs; /* * Some Renesas controllers get into a weird state if they are @@ -265,7 +266,10 @@ static void xhci_zero_64b_regs(struct xhci_hcd *xhci) if (upper_32_bits(val)) xhci_write_64(xhci, 0, &xhci->op_regs->cmd_ring); - for (i = 0; i < HCS_MAX_INTRS(xhci->hcs_params1); i++) { + intrs = min_t(u32, HCS_MAX_INTRS(xhci->hcs_params1), + ARRAY_SIZE(xhci->run_regs->ir_set)); + + for (i = 0; i < intrs; i++) { struct xhci_intr_reg __iomem *ir; ir = &xhci->run_regs->ir_set[i]; @@ -1370,7 +1374,7 @@ static int xhci_configure_endpoint(struct xhci_hcd *xhci, * we need to issue an evaluate context command and wait on it. */ static int xhci_check_maxpacket(struct xhci_hcd *xhci, unsigned int slot_id, - unsigned int ep_index, struct urb *urb) + unsigned int ep_index, struct urb *urb, gfp_t mem_flags) { struct xhci_container_ctx *out_ctx; struct xhci_input_control_ctx *ctrl_ctx; @@ -1401,7 +1405,7 @@ static int xhci_check_maxpacket(struct xhci_hcd *xhci, unsigned int slot_id, * changes max packet sizes. */ - command = xhci_alloc_command(xhci, true, GFP_KERNEL); + command = xhci_alloc_command(xhci, true, mem_flags); if (!command) return -ENOMEM; @@ -1498,7 +1502,7 @@ static int xhci_urb_enqueue(struct usb_hcd *hcd, struct urb *urb, gfp_t mem_flag */ if (urb->dev->speed == USB_SPEED_FULL) { ret = xhci_check_maxpacket(xhci, slot_id, - ep_index, urb); + ep_index, urb, mem_flags); if (ret < 0) { xhci_urb_free_priv(urb_priv); urb->hcpriv = NULL; @@ -3148,6 +3152,14 @@ static void xhci_endpoint_reset(struct usb_hcd *hcd, /* config ep command clears toggle if add and drop ep flags are set */ ctrl_ctx = xhci_get_input_control_ctx(cfg_cmd->in_ctx); + if (!ctrl_ctx) { + spin_unlock_irqrestore(&xhci->lock, flags); + xhci_free_command(xhci, cfg_cmd); + xhci_warn(xhci, "%s: Could not get input context, bad type.\n", + __func__); + goto cleanup; + } + xhci_setup_input_ctx_for_config_ep(xhci, cfg_cmd->in_ctx, vdev->out_ctx, ctrl_ctx, ep_flag, ep_flag); xhci_endpoint_copy(xhci, cfg_cmd->in_ctx, vdev->out_ctx, ep_index); diff --git a/drivers/usb/typec/tcpci.c b/drivers/usb/typec/tcpci.c index dfae41fe13310..2c34add377085 100644 --- a/drivers/usb/typec/tcpci.c +++ b/drivers/usb/typec/tcpci.c @@ -20,6 +20,15 @@ #define PD_RETRY_COUNT 3 +#define tcpc_presenting_cc1_rd(reg) \ + (!(TCPC_ROLE_CTRL_DRP & (reg)) && \ + (((reg) & (TCPC_ROLE_CTRL_CC1_MASK << TCPC_ROLE_CTRL_CC1_SHIFT)) == \ + (TCPC_ROLE_CTRL_CC_RD << TCPC_ROLE_CTRL_CC1_SHIFT))) +#define tcpc_presenting_cc2_rd(reg) \ + (!(TCPC_ROLE_CTRL_DRP & (reg)) && \ + (((reg) & (TCPC_ROLE_CTRL_CC2_MASK << TCPC_ROLE_CTRL_CC2_SHIFT)) == \ + (TCPC_ROLE_CTRL_CC_RD << TCPC_ROLE_CTRL_CC2_SHIFT))) + struct tcpci { struct device *dev; @@ -168,19 +177,25 @@ static int tcpci_get_cc(struct tcpc_dev *tcpc, enum typec_cc_status *cc1, enum typec_cc_status *cc2) { struct tcpci *tcpci = tcpc_to_tcpci(tcpc); - unsigned int reg; + unsigned int reg, role_control; int ret; + ret = regmap_read(tcpci->regmap, TCPC_ROLE_CTRL, &role_control); + if (ret < 0) + return ret; + ret = regmap_read(tcpci->regmap, TCPC_CC_STATUS, ®); if (ret < 0) return ret; *cc1 = tcpci_to_typec_cc((reg >> TCPC_CC_STATUS_CC1_SHIFT) & TCPC_CC_STATUS_CC1_MASK, - reg & TCPC_CC_STATUS_TERM); + reg & TCPC_CC_STATUS_TERM || + tcpc_presenting_cc1_rd(role_control)); *cc2 = tcpci_to_typec_cc((reg >> TCPC_CC_STATUS_CC2_SHIFT) & TCPC_CC_STATUS_CC2_MASK, - reg & TCPC_CC_STATUS_TERM); + reg & TCPC_CC_STATUS_TERM || + tcpc_presenting_cc2_rd(role_control)); return 0; } diff --git a/drivers/usb/usbip/vudc_sysfs.c b/drivers/usb/usbip/vudc_sysfs.c index de2babadd1465..7b1437a51304a 100644 --- a/drivers/usb/usbip/vudc_sysfs.c +++ b/drivers/usb/usbip/vudc_sysfs.c @@ -157,12 +157,14 @@ static ssize_t usbip_sockfd_store(struct device *dev, tcp_rx = kthread_create(&v_rx_loop, &udc->ud, "vudc_rx"); if (IS_ERR(tcp_rx)) { sockfd_put(socket); + mutex_unlock(&udc->ud.sysfs_lock); return -EINVAL; } tcp_tx = kthread_create(&v_tx_loop, &udc->ud, "vudc_tx"); if (IS_ERR(tcp_tx)) { kthread_stop(tcp_rx); sockfd_put(socket); + mutex_unlock(&udc->ud.sysfs_lock); return -EINVAL; } diff --git a/drivers/vfio/mdev/mdev_sysfs.c b/drivers/vfio/mdev/mdev_sysfs.c index 1692a0cc30360..c99fcc6c2eba8 100644 --- a/drivers/vfio/mdev/mdev_sysfs.c +++ b/drivers/vfio/mdev/mdev_sysfs.c @@ -108,6 +108,7 @@ struct mdev_type *add_mdev_supported_type(struct mdev_parent *parent, return ERR_PTR(-ENOMEM); type->kobj.kset = parent->mdev_types_kset; + type->parent = parent; ret = kobject_init_and_add(&type->kobj, &mdev_type_ktype, NULL, "%s-%s", dev_driver_string(parent->dev), @@ -135,7 +136,6 @@ struct mdev_type *add_mdev_supported_type(struct mdev_parent *parent, } type->group = group; - type->parent = parent; return type; attrs_failed: diff --git a/drivers/video/fbdev/core/fbcmap.c b/drivers/video/fbdev/core/fbcmap.c index 2811c4afde01c..e8ea768481049 100644 --- a/drivers/video/fbdev/core/fbcmap.c +++ b/drivers/video/fbdev/core/fbcmap.c @@ -101,17 +101,17 @@ int fb_alloc_cmap_gfp(struct fb_cmap *cmap, int len, int transp, gfp_t flags) if (!len) return 0; - cmap->red = kmalloc(size, flags); + cmap->red = kzalloc(size, flags); if (!cmap->red) goto fail; - cmap->green = kmalloc(size, flags); + cmap->green = kzalloc(size, flags); if (!cmap->green) goto fail; - cmap->blue = kmalloc(size, flags); + cmap->blue = kzalloc(size, flags); if (!cmap->blue) goto fail; if (transp) { - cmap->transp = kmalloc(size, flags); + cmap->transp = kzalloc(size, flags); if (!cmap->transp) goto fail; } else { diff --git a/fs/block_dev.c b/fs/block_dev.c index 9f3faac490259..b34f76af59c4f 100644 --- a/fs/block_dev.c +++ b/fs/block_dev.c @@ -1919,6 +1919,7 @@ ssize_t blkdev_write_iter(struct kiocb *iocb, struct iov_iter *from) struct inode *bd_inode = bdev_file_inode(file); loff_t size = i_size_read(bd_inode); struct blk_plug plug; + size_t shorted = 0; ssize_t ret; if (bdev_read_only(I_BDEV(bd_inode))) @@ -1933,12 +1934,17 @@ ssize_t blkdev_write_iter(struct kiocb *iocb, struct iov_iter *from) if ((iocb->ki_flags & (IOCB_NOWAIT | IOCB_DIRECT)) == IOCB_NOWAIT) return -EOPNOTSUPP; - iov_iter_truncate(from, size - iocb->ki_pos); + size -= iocb->ki_pos; + if (iov_iter_count(from) > size) { + shorted = iov_iter_count(from) - size; + iov_iter_truncate(from, size); + } blk_start_plug(&plug); ret = __generic_file_write_iter(iocb, from); if (ret > 0) ret = generic_write_sync(iocb, ret); + iov_iter_reexpand(from, iov_iter_count(from) + shorted); blk_finish_plug(&plug); return ret; } @@ -1950,13 +1956,21 @@ ssize_t blkdev_read_iter(struct kiocb *iocb, struct iov_iter *to) struct inode *bd_inode = bdev_file_inode(file); loff_t size = i_size_read(bd_inode); loff_t pos = iocb->ki_pos; + size_t shorted = 0; + ssize_t ret; if (pos >= size) return 0; size -= pos; - iov_iter_truncate(to, size); - return generic_file_read_iter(iocb, to); + if (iov_iter_count(to) > size) { + shorted = iov_iter_count(to) - size; + iov_iter_truncate(to, size); + } + + ret = generic_file_read_iter(iocb, to); + iov_iter_reexpand(to, iov_iter_count(to) + shorted); + return ret; } EXPORT_SYMBOL_GPL(blkdev_read_iter); diff --git a/fs/btrfs/ctree.c b/fs/btrfs/ctree.c index 2bdd24425a683..00dc1b5c87372 100644 --- a/fs/btrfs/ctree.c +++ b/fs/btrfs/ctree.c @@ -1414,10 +1414,30 @@ get_old_root(struct btrfs_root *root, u64 time_seq) "failed to read tree block %llu from get_old_root", logical); } else { + struct tree_mod_elem *tm2; + btrfs_tree_read_lock(old); eb = btrfs_clone_extent_buffer(old); + /* + * After the lookup for the most recent tree mod operation + * above and before we locked and cloned the extent buffer + * 'old', a new tree mod log operation may have been added. + * So lookup for a more recent one to make sure the number + * of mod log operations we replay is consistent with the + * number of items we have in the cloned extent buffer, + * otherwise we can hit a BUG_ON when rewinding the extent + * buffer. + */ + tm2 = tree_mod_log_search(fs_info, logical, time_seq); btrfs_tree_read_unlock(old); free_extent_buffer(old); + ASSERT(tm2); + ASSERT(tm2 == tm || tm2->seq > tm->seq); + if (!tm2 || tm2->seq < tm->seq) { + free_extent_buffer(eb); + return NULL; + } + tm = tm2; } } else if (old_root) { eb_root_owner = btrfs_header_owner(eb_root); diff --git a/fs/btrfs/ioctl.c b/fs/btrfs/ioctl.c index 1c053e10b33ba..717385b7f66f7 100644 --- a/fs/btrfs/ioctl.c +++ b/fs/btrfs/ioctl.c @@ -656,8 +656,6 @@ static noinline int create_subvol(struct inode *dir, btrfs_set_root_otransid(root_item, trans->transid); btrfs_tree_unlock(leaf); - free_extent_buffer(leaf); - leaf = NULL; btrfs_set_root_dirid(root_item, new_dirid); @@ -666,8 +664,22 @@ static noinline int create_subvol(struct inode *dir, key.type = BTRFS_ROOT_ITEM_KEY; ret = btrfs_insert_root(trans, fs_info->tree_root, &key, root_item); - if (ret) + if (ret) { + /* + * Since we don't abort the transaction in this case, free the + * tree block so that we don't leak space and leave the + * filesystem in an inconsistent state (an extent item in the + * extent tree without backreferences). Also no need to have + * the tree block locked since it is not in any tree at this + * point, so no other task can find it and use it. + */ + btrfs_free_tree_block(trans, root, leaf, 0, 1); + free_extent_buffer(leaf); goto fail; + } + + free_extent_buffer(leaf); + leaf = NULL; key.offset = (u64)-1; new_root = btrfs_read_fs_root_no_name(fs_info, &key); diff --git a/fs/btrfs/relocation.c b/fs/btrfs/relocation.c index e6e4e6fb2adde..06c6a66a991f2 100644 --- a/fs/btrfs/relocation.c +++ b/fs/btrfs/relocation.c @@ -1755,8 +1755,8 @@ int replace_path(struct btrfs_trans_handle *trans, int ret; int slot; - BUG_ON(src->root_key.objectid != BTRFS_TREE_RELOC_OBJECTID); - BUG_ON(dest->root_key.objectid == BTRFS_TREE_RELOC_OBJECTID); + ASSERT(src->root_key.objectid == BTRFS_TREE_RELOC_OBJECTID); + ASSERT(dest->root_key.objectid != BTRFS_TREE_RELOC_OBJECTID); last_snapshot = btrfs_root_last_snapshot(&src->root_item); again: @@ -1790,7 +1790,7 @@ again: struct btrfs_key first_key; level = btrfs_header_level(parent); - BUG_ON(level < lowest_level); + ASSERT(level >= lowest_level); ret = btrfs_bin_search(parent, &key, level, &slot); if (ret && slot > 0) diff --git a/fs/ceph/caps.c b/fs/ceph/caps.c index 6e871a382209b..918781c51f0ba 100644 --- a/fs/ceph/caps.c +++ b/fs/ceph/caps.c @@ -1779,6 +1779,7 @@ static int try_nonblocking_invalidate(struct inode *inode) u32 invalidating_gen = ci->i_rdcache_gen; spin_unlock(&ci->i_ceph_lock); + ceph_fscache_invalidate(inode); invalidate_mapping_pages(&inode->i_data, 0, -1); spin_lock(&ci->i_ceph_lock); diff --git a/fs/ceph/inode.c b/fs/ceph/inode.c index 3c24fb77ef325..5f041fede7aa9 100644 --- a/fs/ceph/inode.c +++ b/fs/ceph/inode.c @@ -1823,6 +1823,7 @@ static void ceph_invalidate_work(struct work_struct *work) orig_gen = ci->i_rdcache_gen; spin_unlock(&ci->i_ceph_lock); + ceph_fscache_invalidate(inode); if (invalidate_inode_pages2(inode->i_mapping) < 0) { pr_err("invalidate_pages %p fails\n", inode); } diff --git a/fs/cifs/smb2ops.c b/fs/cifs/smb2ops.c index faafa9a557c23..9d94abaff8fc4 100644 --- a/fs/cifs/smb2ops.c +++ b/fs/cifs/smb2ops.c @@ -2700,7 +2700,7 @@ smb2_get_enc_key(struct TCP_Server_Info *server, __u64 ses_id, int enc, u8 *key) } spin_unlock(&cifs_tcp_ses_lock); - return 1; + return -EAGAIN; } /* * Encrypt or decrypt @rqst message. @rqst[0] has the following format: diff --git a/fs/dlm/debug_fs.c b/fs/dlm/debug_fs.c index fa08448e35dd7..bb87dad03cd40 100644 --- a/fs/dlm/debug_fs.c +++ b/fs/dlm/debug_fs.c @@ -544,6 +544,7 @@ static void *table_seq_next(struct seq_file *seq, void *iter_ptr, loff_t *pos) if (bucket >= ls->ls_rsbtbl_size) { kfree(ri); + ++*pos; return NULL; } tree = toss ? &ls->ls_rsbtbl[bucket].toss : &ls->ls_rsbtbl[bucket].keep; diff --git a/fs/ecryptfs/main.c b/fs/ecryptfs/main.c index 025d66a705db6..b86a9b3a39c06 100644 --- a/fs/ecryptfs/main.c +++ b/fs/ecryptfs/main.c @@ -506,6 +506,12 @@ static struct dentry *ecryptfs_mount(struct file_system_type *fs_type, int flags goto out; } + if (!dev_name) { + rc = -EINVAL; + err = "Device name cannot be null"; + goto out; + } + rc = ecryptfs_parse_options(sbi, raw_data, &check_ruid); if (rc) { err = "Error parsing options"; diff --git a/fs/ext4/ialloc.c b/fs/ext4/ialloc.c index 8876eaad10f68..16abe23b1417a 100644 --- a/fs/ext4/ialloc.c +++ b/fs/ext4/ialloc.c @@ -1358,6 +1358,7 @@ int ext4_init_inode_table(struct super_block *sb, ext4_group_t group, handle_t *handle; ext4_fsblk_t blk; int num, ret = 0, used_blks = 0; + unsigned long used_inos = 0; /* This should not happen, but just to be sure check this */ if (sb_rdonly(sb)) { @@ -1388,22 +1389,37 @@ int ext4_init_inode_table(struct super_block *sb, ext4_group_t group, * used inodes so we need to skip blocks with used inodes in * inode table. */ - if (!(gdp->bg_flags & cpu_to_le16(EXT4_BG_INODE_UNINIT))) - used_blks = DIV_ROUND_UP((EXT4_INODES_PER_GROUP(sb) - - ext4_itable_unused_count(sb, gdp)), - sbi->s_inodes_per_block); - - if ((used_blks < 0) || (used_blks > sbi->s_itb_per_group) || - ((group == 0) && ((EXT4_INODES_PER_GROUP(sb) - - ext4_itable_unused_count(sb, gdp)) < - EXT4_FIRST_INO(sb)))) { - ext4_error(sb, "Something is wrong with group %u: " - "used itable blocks: %d; " - "itable unused count: %u", - group, used_blks, - ext4_itable_unused_count(sb, gdp)); - ret = 1; - goto err_out; + if (!(gdp->bg_flags & cpu_to_le16(EXT4_BG_INODE_UNINIT))) { + used_inos = EXT4_INODES_PER_GROUP(sb) - + ext4_itable_unused_count(sb, gdp); + used_blks = DIV_ROUND_UP(used_inos, sbi->s_inodes_per_block); + + /* Bogus inode unused count? */ + if (used_blks < 0 || used_blks > sbi->s_itb_per_group) { + ext4_error(sb, "Something is wrong with group %u: " + "used itable blocks: %d; " + "itable unused count: %u", + group, used_blks, + ext4_itable_unused_count(sb, gdp)); + ret = 1; + goto err_out; + } + + used_inos += group * EXT4_INODES_PER_GROUP(sb); + /* + * Are there some uninitialized inodes in the inode table + * before the first normal inode? + */ + if ((used_blks != sbi->s_itb_per_group) && + (used_inos < EXT4_FIRST_INO(sb))) { + ext4_error(sb, "Something is wrong with group %u: " + "itable unused count: %u; " + "itables initialized count: %ld", + group, ext4_itable_unused_count(sb, gdp), + used_inos); + ret = 1; + goto err_out; + } } blk = ext4_inode_table(sb, gdp) + used_blks; diff --git a/fs/ext4/super.c b/fs/ext4/super.c index e9e9f09f5370d..535ab6713732a 100644 --- a/fs/ext4/super.c +++ b/fs/ext4/super.c @@ -2629,9 +2629,6 @@ static void ext4_orphan_cleanup(struct super_block *sb, sb->s_flags &= ~SB_RDONLY; } #ifdef CONFIG_QUOTA - /* Needed for iput() to work correctly and not trash data */ - sb->s_flags |= SB_ACTIVE; - /* * Turn on quotas which were not enabled for read-only mounts if * filesystem has quota feature, so that they are updated correctly. @@ -4962,8 +4959,10 @@ static int ext4_commit_super(struct super_block *sb, int sync) struct buffer_head *sbh = EXT4_SB(sb)->s_sbh; int error = 0; - if (!sbh || block_device_ejected(sb)) - return error; + if (!sbh) + return -EINVAL; + if (block_device_ejected(sb)) + return -ENODEV; /* * If the file system is mounted read-only, don't update the diff --git a/fs/f2fs/inline.c b/fs/f2fs/inline.c index 299f295fcb6c7..6bf78cf63ea2e 100644 --- a/fs/f2fs/inline.c +++ b/fs/f2fs/inline.c @@ -220,7 +220,8 @@ out: f2fs_put_page(page, 1); - f2fs_balance_fs(sbi, dn.node_changed); + if (!err) + f2fs_balance_fs(sbi, dn.node_changed); return err; } diff --git a/fs/f2fs/node.c b/fs/f2fs/node.c index 1934dc6ad1ccd..ff3f97ba1a555 100644 --- a/fs/f2fs/node.c +++ b/fs/f2fs/node.c @@ -2654,6 +2654,9 @@ static void remove_nats_in_journal(struct f2fs_sb_info *sbi) struct f2fs_nat_entry raw_ne; nid_t nid = le32_to_cpu(nid_in_journal(journal, i)); + if (f2fs_check_nid_range(sbi, nid)) + continue; + raw_ne = nat_in_journal(journal, i); ne = __lookup_nat_cache(nm_i, nid); diff --git a/fs/fuse/cuse.c b/fs/fuse/cuse.c index f057c213c453a..e10e2b62ccf45 100644 --- a/fs/fuse/cuse.c +++ b/fs/fuse/cuse.c @@ -621,6 +621,8 @@ static int __init cuse_init(void) cuse_channel_fops.owner = THIS_MODULE; cuse_channel_fops.open = cuse_channel_open; cuse_channel_fops.release = cuse_channel_release; + /* CUSE is not prepared for FUSE_DEV_IOC_CLONE */ + cuse_channel_fops.unlocked_ioctl = NULL; cuse_class = class_create(THIS_MODULE, "cuse"); if (IS_ERR(cuse_class)) diff --git a/fs/hfsplus/extents.c b/fs/hfsplus/extents.c index a930ddd156819..7054a542689f9 100644 --- a/fs/hfsplus/extents.c +++ b/fs/hfsplus/extents.c @@ -598,13 +598,15 @@ void hfsplus_file_truncate(struct inode *inode) res = __hfsplus_ext_cache_extent(&fd, inode, alloc_cnt); if (res) break; - hfs_brec_remove(&fd); - mutex_unlock(&fd.tree->tree_lock); start = hip->cached_start; + if (blk_cnt <= start) + hfs_brec_remove(&fd); + mutex_unlock(&fd.tree->tree_lock); hfsplus_free_extents(sb, hip->cached_extents, alloc_cnt - start, alloc_cnt - blk_cnt); hfsplus_dump_extent(hip->cached_extents); + mutex_lock(&fd.tree->tree_lock); if (blk_cnt > start) { hip->extent_state |= HFSPLUS_EXT_DIRTY; break; @@ -612,7 +614,6 @@ void hfsplus_file_truncate(struct inode *inode) alloc_cnt = start; hip->cached_start = hip->cached_blocks = 0; hip->extent_state &= ~(HFSPLUS_EXT_DIRTY | HFSPLUS_EXT_NEW); - mutex_lock(&fd.tree->tree_lock); } hfs_find_exit(&fd); diff --git a/fs/iomap.c b/fs/iomap.c index 03edf62633dcc..ac7b2152c3ad1 100644 --- a/fs/iomap.c +++ b/fs/iomap.c @@ -116,6 +116,7 @@ iomap_page_create(struct inode *inode, struct page *page) iop = kmalloc(sizeof(*iop), GFP_NOFS | __GFP_NOFAIL); atomic_set(&iop->read_count, 0); atomic_set(&iop->write_count, 0); + spin_lock_init(&iop->uptodate_lock); bitmap_zero(iop->uptodate, PAGE_SIZE / SECTOR_SIZE); /* @@ -204,25 +205,38 @@ iomap_adjust_read_range(struct inode *inode, struct iomap_page *iop, } static void -iomap_set_range_uptodate(struct page *page, unsigned off, unsigned len) +iomap_iop_set_range_uptodate(struct page *page, unsigned off, unsigned len) { struct iomap_page *iop = to_iomap_page(page); struct inode *inode = page->mapping->host; unsigned first = off >> inode->i_blkbits; unsigned last = (off + len - 1) >> inode->i_blkbits; - unsigned int i; bool uptodate = true; + unsigned long flags; + unsigned int i; - if (iop) { - for (i = 0; i < PAGE_SIZE / i_blocksize(inode); i++) { - if (i >= first && i <= last) - set_bit(i, iop->uptodate); - else if (!test_bit(i, iop->uptodate)) - uptodate = false; - } + spin_lock_irqsave(&iop->uptodate_lock, flags); + for (i = 0; i < PAGE_SIZE / i_blocksize(inode); i++) { + if (i >= first && i <= last) + set_bit(i, iop->uptodate); + else if (!test_bit(i, iop->uptodate)) + uptodate = false; } - if (uptodate && !PageError(page)) + if (uptodate) + SetPageUptodate(page); + spin_unlock_irqrestore(&iop->uptodate_lock, flags); +} + +static void +iomap_set_range_uptodate(struct page *page, unsigned off, unsigned len) +{ + if (PageError(page)) + return; + + if (page_has_private(page)) + iomap_iop_set_range_uptodate(page, off, len); + else SetPageUptodate(page); } diff --git a/fs/jffs2/compr_rtime.c b/fs/jffs2/compr_rtime.c index 406d9cc84ba8d..79e771ab624f4 100644 --- a/fs/jffs2/compr_rtime.c +++ b/fs/jffs2/compr_rtime.c @@ -37,6 +37,9 @@ static int jffs2_rtime_compress(unsigned char *data_in, int outpos = 0; int pos=0; + if (*dstlen <= 3) + return -1; + memset(positions,0,sizeof(positions)); while (pos < (*sourcelen) && outpos <= (*dstlen)-2) { diff --git a/fs/jffs2/scan.c b/fs/jffs2/scan.c index 90431dd613b8d..08813789fcf06 100644 --- a/fs/jffs2/scan.c +++ b/fs/jffs2/scan.c @@ -1075,7 +1075,7 @@ static int jffs2_scan_dirent_node(struct jffs2_sb_info *c, struct jffs2_eraseblo memcpy(&fd->name, rd->name, checkedlen); fd->name[checkedlen] = 0; - crc = crc32(0, fd->name, rd->nsize); + crc = crc32(0, fd->name, checkedlen); if (crc != je32_to_cpu(rd->name_crc)) { pr_notice("%s(): Name CRC failed on node at 0x%08x: Read 0x%08x, calculated 0x%08x\n", __func__, ofs, je32_to_cpu(rd->name_crc), crc); diff --git a/fs/nfs/flexfilelayout/flexfilelayout.c b/fs/nfs/flexfilelayout/flexfilelayout.c index d8cba46a9395c..fee421da21975 100644 --- a/fs/nfs/flexfilelayout/flexfilelayout.c +++ b/fs/nfs/flexfilelayout/flexfilelayout.c @@ -101,7 +101,7 @@ static int decode_nfs_fh(struct xdr_stream *xdr, struct nfs_fh *fh) if (unlikely(!p)) return -ENOBUFS; fh->size = be32_to_cpup(p++); - if (fh->size > sizeof(struct nfs_fh)) { + if (fh->size > NFS_MAXFHSIZE) { printk(KERN_ERR "NFS flexfiles: Too big fh received %d\n", fh->size); return -EOVERFLOW; diff --git a/fs/nfs/inode.c b/fs/nfs/inode.c index aee66d8f13305..dc55ecc3bec46 100644 --- a/fs/nfs/inode.c +++ b/fs/nfs/inode.c @@ -1607,10 +1607,10 @@ EXPORT_SYMBOL_GPL(_nfs_display_fhandle); */ static int nfs_inode_attrs_need_update(const struct inode *inode, const struct nfs_fattr *fattr) { - const struct nfs_inode *nfsi = NFS_I(inode); + unsigned long attr_gencount = NFS_I(inode)->attr_gencount; - return ((long)fattr->gencount - (long)nfsi->attr_gencount) > 0 || - ((long)nfsi->attr_gencount - (long)nfs_read_attr_generation_counter() > 0); + return (long)(fattr->gencount - attr_gencount) > 0 || + (long)(attr_gencount - nfs_read_attr_generation_counter()) > 0; } static int nfs_refresh_inode_locked(struct inode *inode, struct nfs_fattr *fattr) @@ -2034,7 +2034,7 @@ static int nfs_update_inode(struct inode *inode, struct nfs_fattr *fattr) nfsi->attrtimeo_timestamp = now; } /* Set the barrier to be more recent than this fattr */ - if ((long)fattr->gencount - (long)nfsi->attr_gencount > 0) + if ((long)(fattr->gencount - nfsi->attr_gencount) > 0) nfsi->attr_gencount = fattr->gencount; } diff --git a/fs/nfs/nfs42proc.c b/fs/nfs/nfs42proc.c index 526441de89c1d..be252795a6f70 100644 --- a/fs/nfs/nfs42proc.c +++ b/fs/nfs/nfs42proc.c @@ -59,7 +59,8 @@ static int _nfs42_proc_fallocate(struct rpc_message *msg, struct file *filep, static int nfs42_proc_fallocate(struct rpc_message *msg, struct file *filep, loff_t offset, loff_t len) { - struct nfs_server *server = NFS_SERVER(file_inode(filep)); + struct inode *inode = file_inode(filep); + struct nfs_server *server = NFS_SERVER(inode); struct nfs4_exception exception = { }; struct nfs_lock_context *lock; int err; @@ -68,9 +69,13 @@ static int nfs42_proc_fallocate(struct rpc_message *msg, struct file *filep, if (IS_ERR(lock)) return PTR_ERR(lock); - exception.inode = file_inode(filep); + exception.inode = inode; exception.state = lock->open_context->state; + err = nfs_sync_inode(inode); + if (err) + goto out; + do { err = _nfs42_proc_fallocate(msg, filep, lock, offset, len); if (err == -ENOTSUPP) { @@ -79,7 +84,7 @@ static int nfs42_proc_fallocate(struct rpc_message *msg, struct file *filep, } err = nfs4_handle_exception(server, err, &exception); } while (exception.retry); - +out: nfs_put_lock_context(lock); return err; } @@ -117,16 +122,13 @@ int nfs42_proc_deallocate(struct file *filep, loff_t offset, loff_t len) return -EOPNOTSUPP; inode_lock(inode); - err = nfs_sync_inode(inode); - if (err) - goto out_unlock; err = nfs42_proc_fallocate(&msg, filep, offset, len); if (err == 0) truncate_pagecache_range(inode, offset, (offset + len) -1); if (err == -EOPNOTSUPP) NFS_SERVER(inode)->caps &= ~NFS_CAP_DEALLOCATE; -out_unlock: + inode_unlock(inode); return err; } @@ -498,7 +500,10 @@ static loff_t _nfs42_proc_llseek(struct file *filep, if (status) return status; - return vfs_setpos(filep, res.sr_offset, inode->i_sb->s_maxbytes); + if (whence == SEEK_DATA && res.sr_eof) + return -NFS4ERR_NXIO; + else + return vfs_setpos(filep, res.sr_offset, inode->i_sb->s_maxbytes); } loff_t nfs42_proc_llseek(struct file *filep, loff_t offset, int whence) diff --git a/fs/nfs/pnfs.c b/fs/nfs/pnfs.c index 55965e8e9a2ed..af255109c5bf9 100644 --- a/fs/nfs/pnfs.c +++ b/fs/nfs/pnfs.c @@ -1294,7 +1294,7 @@ _pnfs_return_layout(struct inode *ino) } valid_layout = pnfs_layout_is_valid(lo); pnfs_clear_layoutcommit(ino, &tmp_list); - pnfs_mark_matching_lsegs_invalid(lo, &tmp_list, NULL, 0); + pnfs_mark_matching_lsegs_return(lo, &tmp_list, NULL, 0); if (NFS_SERVER(ino)->pnfs_curr_ld->return_range) { struct pnfs_layout_range range = { @@ -2359,6 +2359,9 @@ pnfs_mark_matching_lsegs_return(struct pnfs_layout_hdr *lo, assert_spin_locked(&lo->plh_inode->i_lock); + if (test_bit(NFS_LAYOUT_RETURN_REQUESTED, &lo->plh_flags)) + tmp_list = &lo->plh_return_segs; + list_for_each_entry_safe(lseg, next, &lo->plh_segs, pls_list) if (pnfs_match_lseg_recall(lseg, return_range, seq)) { dprintk("%s: marking lseg %p iomode %d " @@ -2366,6 +2369,8 @@ pnfs_mark_matching_lsegs_return(struct pnfs_layout_hdr *lo, lseg, lseg->pls_range.iomode, lseg->pls_range.offset, lseg->pls_range.length); + if (test_bit(NFS_LSEG_LAYOUTRETURN, &lseg->pls_flags)) + tmp_list = &lo->plh_return_segs; if (mark_lseg_invalid(lseg, tmp_list)) continue; remaining++; diff --git a/fs/overlayfs/copy_up.c b/fs/overlayfs/copy_up.c index e164f489d01d9..30abafcd4ecce 100644 --- a/fs/overlayfs/copy_up.c +++ b/fs/overlayfs/copy_up.c @@ -824,7 +824,7 @@ static int ovl_copy_up_one(struct dentry *parent, struct dentry *dentry, int ovl_copy_up_flags(struct dentry *dentry, int flags) { int err = 0; - const struct cred *old_cred = ovl_override_creds(dentry->d_sb); + const struct cred *old_cred; bool disconnected = (dentry->d_flags & DCACHE_DISCONNECTED); /* @@ -835,6 +835,7 @@ int ovl_copy_up_flags(struct dentry *dentry, int flags) if (WARN_ON(disconnected && d_is_dir(dentry))) return -EIO; + old_cred = ovl_override_creds(dentry->d_sb); while (!err) { struct dentry *next; struct dentry *parent = NULL; diff --git a/fs/squashfs/file.c b/fs/squashfs/file.c index f1c1430ae7213..0bcb83479fcba 100644 --- a/fs/squashfs/file.c +++ b/fs/squashfs/file.c @@ -224,11 +224,11 @@ failure: * If the skip factor is limited in this way then the file will use multiple * slots. */ -static inline int calculate_skip(int blocks) +static inline int calculate_skip(u64 blocks) { - int skip = blocks / ((SQUASHFS_META_ENTRIES + 1) + u64 skip = blocks / ((SQUASHFS_META_ENTRIES + 1) * SQUASHFS_META_INDEXES); - return min(SQUASHFS_CACHED_BLKS - 1, skip + 1); + return min((u64) SQUASHFS_CACHED_BLKS - 1, skip + 1); } diff --git a/fs/ubifs/replay.c b/fs/ubifs/replay.c index c6f9b2225387f..673d1f08b9a4b 100644 --- a/fs/ubifs/replay.c +++ b/fs/ubifs/replay.c @@ -232,7 +232,8 @@ static bool inode_still_linked(struct ubifs_info *c, struct replay_entry *rino) */ list_for_each_entry_reverse(r, &c->replay_list, list) { ubifs_assert(c, r->sqnum >= rino->sqnum); - if (key_inum(c, &r->key) == key_inum(c, &rino->key)) + if (key_inum(c, &r->key) == key_inum(c, &rino->key) && + key_type(c, &r->key) == UBIFS_INO_KEY) return r->deletion == 0; } diff --git a/include/crypto/acompress.h b/include/crypto/acompress.h index e328b52425a85..1ff78365607cd 100644 --- a/include/crypto/acompress.h +++ b/include/crypto/acompress.h @@ -152,6 +152,8 @@ static inline struct crypto_acomp *crypto_acomp_reqtfm(struct acomp_req *req) * crypto_free_acomp() -- free ACOMPRESS tfm handle * * @tfm: ACOMPRESS tfm handle allocated with crypto_alloc_acomp() + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_acomp(struct crypto_acomp *tfm) { diff --git a/include/crypto/aead.h b/include/crypto/aead.h index 1e26f790b03fa..c69c545ba39a9 100644 --- a/include/crypto/aead.h +++ b/include/crypto/aead.h @@ -187,6 +187,8 @@ static inline struct crypto_tfm *crypto_aead_tfm(struct crypto_aead *tfm) /** * crypto_free_aead() - zeroize and free aead handle * @tfm: cipher handle to be freed + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_aead(struct crypto_aead *tfm) { diff --git a/include/crypto/akcipher.h b/include/crypto/akcipher.h index b5e11de4d497d..9817f2e5bff83 100644 --- a/include/crypto/akcipher.h +++ b/include/crypto/akcipher.h @@ -174,6 +174,8 @@ static inline struct crypto_akcipher *crypto_akcipher_reqtfm( * crypto_free_akcipher() - free AKCIPHER tfm handle * * @tfm: AKCIPHER tfm handle allocated with crypto_alloc_akcipher() + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_akcipher(struct crypto_akcipher *tfm) { diff --git a/include/crypto/hash.h b/include/crypto/hash.h index 76e432cab75db..552517dcf9e4f 100644 --- a/include/crypto/hash.h +++ b/include/crypto/hash.h @@ -257,6 +257,8 @@ static inline struct crypto_tfm *crypto_ahash_tfm(struct crypto_ahash *tfm) /** * crypto_free_ahash() - zeroize and free the ahash handle * @tfm: cipher handle to be freed + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_ahash(struct crypto_ahash *tfm) { @@ -692,6 +694,8 @@ static inline struct crypto_tfm *crypto_shash_tfm(struct crypto_shash *tfm) /** * crypto_free_shash() - zeroize and free the message digest handle * @tfm: cipher handle to be freed + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_shash(struct crypto_shash *tfm) { diff --git a/include/crypto/kpp.h b/include/crypto/kpp.h index 1bde0a6514fa6..1a34630fc3718 100644 --- a/include/crypto/kpp.h +++ b/include/crypto/kpp.h @@ -159,6 +159,8 @@ static inline void crypto_kpp_set_flags(struct crypto_kpp *tfm, u32 flags) * crypto_free_kpp() - free KPP tfm handle * * @tfm: KPP tfm handle allocated with crypto_alloc_kpp() + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_kpp(struct crypto_kpp *tfm) { diff --git a/include/crypto/rng.h b/include/crypto/rng.h index b95ede354a665..a788c1e5a1217 100644 --- a/include/crypto/rng.h +++ b/include/crypto/rng.h @@ -116,6 +116,8 @@ static inline struct rng_alg *crypto_rng_alg(struct crypto_rng *tfm) /** * crypto_free_rng() - zeroize and free RNG handle * @tfm: cipher handle to be freed + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_rng(struct crypto_rng *tfm) { diff --git a/include/crypto/skcipher.h b/include/crypto/skcipher.h index 2f327f090c3e9..c7553f8b1bb69 100644 --- a/include/crypto/skcipher.h +++ b/include/crypto/skcipher.h @@ -206,6 +206,8 @@ static inline struct crypto_tfm *crypto_skcipher_tfm( /** * crypto_free_skcipher() - zeroize and free cipher handle * @tfm: cipher handle to be freed + * + * If @tfm is a NULL or error pointer, this function does nothing. */ static inline void crypto_free_skcipher(struct crypto_skcipher *tfm) { diff --git a/include/linux/hid.h b/include/linux/hid.h index a46b6832b3733..4dcce83ca3784 100644 --- a/include/linux/hid.h +++ b/include/linux/hid.h @@ -270,6 +270,8 @@ struct hid_item { #define HID_CP_SELECTION 0x000c0080 #define HID_CP_MEDIASELECTION 0x000c0087 #define HID_CP_SELECTDISC 0x000c00ba +#define HID_CP_VOLUMEUP 0x000c00e9 +#define HID_CP_VOLUMEDOWN 0x000c00ea #define HID_CP_PLAYBACKSPEED 0x000c00f1 #define HID_CP_PROXIMITY 0x000c0109 #define HID_CP_SPEAKERSYSTEM 0x000c0160 diff --git a/include/linux/i2c.h b/include/linux/i2c.h index 7e748648c7d3d..6fda0458745dc 100644 --- a/include/linux/i2c.h +++ b/include/linux/i2c.h @@ -662,6 +662,8 @@ struct i2c_adapter_quirks { #define I2C_AQ_NO_ZERO_LEN_READ BIT(5) #define I2C_AQ_NO_ZERO_LEN_WRITE BIT(6) #define I2C_AQ_NO_ZERO_LEN (I2C_AQ_NO_ZERO_LEN_READ | I2C_AQ_NO_ZERO_LEN_WRITE) +/* adapter cannot do repeated START */ +#define I2C_AQ_NO_REP_START BIT(7) /* * i2c_adapter is the structure used to identify a physical i2c bus along diff --git a/include/linux/iomap.h b/include/linux/iomap.h index 3555d54bf79a5..e93ecacb5eaf3 100644 --- a/include/linux/iomap.h +++ b/include/linux/iomap.h @@ -108,6 +108,7 @@ struct iomap_ops { struct iomap_page { atomic_t read_count; atomic_t write_count; + spinlock_t uptodate_lock; DECLARE_BITMAP(uptodate, PAGE_SIZE / 512); }; diff --git a/include/linux/module.h b/include/linux/module.h index 9915397715fc2..008cfc08a6643 100644 --- a/include/linux/module.h +++ b/include/linux/module.h @@ -359,6 +359,7 @@ struct module { unsigned int num_gpl_syms; const struct kernel_symbol *gpl_syms; const s32 *gpl_crcs; + bool using_gplonly_symbols; #ifdef CONFIG_UNUSED_SYMBOLS /* unused exported symbols. */ @@ -529,34 +530,14 @@ struct module *find_module(const char *name); struct symsearch { const struct kernel_symbol *start, *stop; const s32 *crcs; - enum { + enum mod_license { NOT_GPL_ONLY, GPL_ONLY, WILL_BE_GPL_ONLY, - } licence; + } license; bool unused; }; -/* - * Search for an exported symbol by name. - * - * Must be called with module_mutex held or preemption disabled. - */ -const struct kernel_symbol *find_symbol(const char *name, - struct module **owner, - const s32 **crc, - bool gplok, - bool warn); - -/* - * Walk the exported symbol table - * - * Must be called with module_mutex held or preemption disabled. - */ -bool each_symbol_section(bool (*fn)(const struct symsearch *arr, - struct module *owner, - void *data), void *data); - /* Returns 0 and fills in value, defined and namebuf, or -ERANGE if symnum out of range. */ int module_get_kallsym(unsigned int symnum, unsigned long *value, char *type, @@ -604,7 +585,6 @@ static inline void __module_get(struct module *module) #define symbol_put_addr(p) do { } while (0) #endif /* CONFIG_MODULE_UNLOAD */ -int ref_module(struct module *a, struct module *b); /* This is a #define so the string doesn't get put in every .o file */ #define module_name(mod) \ diff --git a/include/linux/power/bq27xxx_battery.h b/include/linux/power/bq27xxx_battery.h index d6355f49fbae6..13d5dd4eb40b4 100644 --- a/include/linux/power/bq27xxx_battery.h +++ b/include/linux/power/bq27xxx_battery.h @@ -49,7 +49,6 @@ struct bq27xxx_reg_cache { int capacity; int energy; int flags; - int power_avg; int health; }; diff --git a/include/linux/smp.h b/include/linux/smp.h index 9fb239e12b824..6bb7f07bc1dd2 100644 --- a/include/linux/smp.h +++ b/include/linux/smp.h @@ -53,7 +53,7 @@ void on_each_cpu_cond(bool (*cond_func)(int cpu, void *info), smp_call_func_t func, void *info, bool wait, gfp_t gfp_flags); -int smp_call_function_single_async(int cpu, call_single_data_t *csd); +int smp_call_function_single_async(int cpu, struct __call_single_data *csd); #ifdef CONFIG_SMP diff --git a/include/linux/spi/spi.h b/include/linux/spi/spi.h index 8ceba9b8e51e3..16158fe097a82 100644 --- a/include/linux/spi/spi.h +++ b/include/linux/spi/spi.h @@ -450,6 +450,9 @@ struct spi_controller { #define SPI_MASTER_GPIO_SS BIT(5) /* GPIO CS must select slave */ + /* flag indicating this is a non-devres managed controller */ + bool devm_allocated; + /* flag indicating this is an SPI slave controller */ bool slave; diff --git a/include/linux/tty_driver.h b/include/linux/tty_driver.h index 71dbc891851a4..e10b09672345b 100644 --- a/include/linux/tty_driver.h +++ b/include/linux/tty_driver.h @@ -236,7 +236,7 @@ * * Called when the device receives a TIOCGICOUNT ioctl. Passed a kernel * structure to complete. This method is optional and will only be called - * if provided (otherwise EINVAL will be returned). + * if provided (otherwise ENOTTY will be returned). */ #include diff --git a/include/net/bluetooth/hci_core.h b/include/net/bluetooth/hci_core.h index 3195728095752..6a61faf0cc79a 100644 --- a/include/net/bluetooth/hci_core.h +++ b/include/net/bluetooth/hci_core.h @@ -526,6 +526,7 @@ struct hci_chan { struct sk_buff_head data_q; unsigned int sent; __u8 state; + bool amp; }; struct hci_conn_params { diff --git a/include/scsi/libfcoe.h b/include/scsi/libfcoe.h index 58507c7783cf0..eafccb2d4d6f7 100644 --- a/include/scsi/libfcoe.h +++ b/include/scsi/libfcoe.h @@ -261,7 +261,7 @@ int fcoe_ctlr_recv_flogi(struct fcoe_ctlr *, struct fc_lport *, struct fc_frame *); /* libfcoe funcs */ -u64 fcoe_wwn_from_mac(unsigned char mac[], unsigned int, unsigned int); +u64 fcoe_wwn_from_mac(unsigned char mac[MAX_ADDR_LEN], unsigned int, unsigned int); int fcoe_libfc_config(struct fc_lport *, struct fcoe_ctlr *, const struct libfc_function_template *, int init_fcp); u32 fcoe_fc_crc(struct fc_frame *fp); diff --git a/include/uapi/linux/netfilter/xt_SECMARK.h b/include/uapi/linux/netfilter/xt_SECMARK.h index 1f2a708413f5d..beb2cadba8a9c 100644 --- a/include/uapi/linux/netfilter/xt_SECMARK.h +++ b/include/uapi/linux/netfilter/xt_SECMARK.h @@ -20,4 +20,10 @@ struct xt_secmark_target_info { char secctx[SECMARK_SECCTX_MAX]; }; +struct xt_secmark_target_info_v1 { + __u8 mode; + char secctx[SECMARK_SECCTX_MAX]; + __u32 secid; +}; + #endif /*_XT_SECMARK_H_target */ diff --git a/include/uapi/linux/tty_flags.h b/include/uapi/linux/tty_flags.h index 900a32e634247..6a3ac496a56c1 100644 --- a/include/uapi/linux/tty_flags.h +++ b/include/uapi/linux/tty_flags.h @@ -39,7 +39,7 @@ * WARNING: These flags are no longer used and have been superceded by the * TTY_PORT_ flags in the iflags field (and not userspace-visible) */ -#ifndef _KERNEL_ +#ifndef __KERNEL__ #define ASYNCB_INITIALIZED 31 /* Serial port was initialized */ #define ASYNCB_SUSPENDED 30 /* Serial port is suspended */ #define ASYNCB_NORMAL_ACTIVE 29 /* Normal device is active */ @@ -81,7 +81,7 @@ #define ASYNC_SPD_WARP (ASYNC_SPD_HI|ASYNC_SPD_SHI) #define ASYNC_SPD_MASK (ASYNC_SPD_HI|ASYNC_SPD_VHI|ASYNC_SPD_SHI) -#ifndef _KERNEL_ +#ifndef __KERNEL__ /* These flags are no longer used (and were always masked from userspace) */ #define ASYNC_INITIALIZED (1U << ASYNCB_INITIALIZED) #define ASYNC_NORMAL_ACTIVE (1U << ASYNCB_NORMAL_ACTIVE) diff --git a/kernel/futex.c b/kernel/futex.c index 7d0d8a45f9ae7..526ebcff5a0a9 100644 --- a/kernel/futex.c +++ b/kernel/futex.c @@ -3867,8 +3867,7 @@ long do_futex(u32 __user *uaddr, int op, u32 val, ktime_t *timeout, if (op & FUTEX_CLOCK_REALTIME) { flags |= FLAGS_CLOCKRT; - if (cmd != FUTEX_WAIT && cmd != FUTEX_WAIT_BITSET && \ - cmd != FUTEX_WAIT_REQUEUE_PI) + if (cmd != FUTEX_WAIT_BITSET && cmd != FUTEX_WAIT_REQUEUE_PI) return -ENOSYS; } diff --git a/kernel/irq/matrix.c b/kernel/irq/matrix.c index 651a4ad6d711f..8e586858bcf41 100644 --- a/kernel/irq/matrix.c +++ b/kernel/irq/matrix.c @@ -423,7 +423,9 @@ void irq_matrix_free(struct irq_matrix *m, unsigned int cpu, if (WARN_ON_ONCE(bit < m->alloc_start || bit >= m->alloc_end)) return; - clear_bit(bit, cm->alloc_map); + if (WARN_ON_ONCE(!test_and_clear_bit(bit, cm->alloc_map))) + return; + cm->allocated--; if(managed) cm->managed_allocated--; diff --git a/kernel/kexec_file.c b/kernel/kexec_file.c index 2fbdb78d66c80..89d41c0a10f1e 100644 --- a/kernel/kexec_file.c +++ b/kernel/kexec_file.c @@ -631,8 +631,10 @@ static int kexec_calculate_store_digests(struct kimage *image) sha_region_sz = KEXEC_SEGMENT_MAX * sizeof(struct kexec_sha_region); sha_regions = vzalloc(sha_region_sz); - if (!sha_regions) + if (!sha_regions) { + ret = -ENOMEM; goto out_free_desc; + } desc->tfm = tfm; desc->flags = 0; diff --git a/kernel/module.c b/kernel/module.c index d5d01ece720c4..92d8610742c7d 100644 --- a/kernel/module.c +++ b/kernel/module.c @@ -415,7 +415,7 @@ static bool each_symbol_in_section(const struct symsearch *arr, } /* Returns true as soon as fn returns true, otherwise false. */ -bool each_symbol_section(bool (*fn)(const struct symsearch *arr, +static bool each_symbol_section(bool (*fn)(const struct symsearch *arr, struct module *owner, void *data), void *data) @@ -476,7 +476,6 @@ bool each_symbol_section(bool (*fn)(const struct symsearch *arr, } return false; } -EXPORT_SYMBOL_GPL(each_symbol_section); struct find_symbol_arg { /* Input */ @@ -488,6 +487,7 @@ struct find_symbol_arg { struct module *owner; const s32 *crc; const struct kernel_symbol *sym; + enum mod_license license; }; static bool check_symbol(const struct symsearch *syms, @@ -497,9 +497,9 @@ static bool check_symbol(const struct symsearch *syms, struct find_symbol_arg *fsa = data; if (!fsa->gplok) { - if (syms->licence == GPL_ONLY) + if (syms->license == GPL_ONLY) return false; - if (syms->licence == WILL_BE_GPL_ONLY && fsa->warn) { + if (syms->license == WILL_BE_GPL_ONLY && fsa->warn) { pr_warn("Symbol %s is being used by a non-GPL module, " "which will not be allowed in the future\n", fsa->name); @@ -521,6 +521,7 @@ static bool check_symbol(const struct symsearch *syms, fsa->owner = owner; fsa->crc = symversion(syms->crcs, symnum); fsa->sym = &syms->start[symnum]; + fsa->license = syms->license; return true; } @@ -568,9 +569,10 @@ static bool find_symbol_in_section(const struct symsearch *syms, /* Find a symbol and return it, along with, (optional) crc and * (optional) module which owns it. Needs preempt disabled or module_mutex. */ -const struct kernel_symbol *find_symbol(const char *name, +static const struct kernel_symbol *find_symbol(const char *name, struct module **owner, const s32 **crc, + enum mod_license *license, bool gplok, bool warn) { @@ -585,13 +587,14 @@ const struct kernel_symbol *find_symbol(const char *name, *owner = fsa.owner; if (crc) *crc = fsa.crc; + if (license) + *license = fsa.license; return fsa.sym; } pr_debug("Failed to find symbol %s\n", name); return NULL; } -EXPORT_SYMBOL_GPL(find_symbol); /* * Search for module by name: must hold module_mutex (or preempt disabled @@ -851,7 +854,7 @@ static int add_module_usage(struct module *a, struct module *b) } /* Module a uses b: caller needs module_mutex() */ -int ref_module(struct module *a, struct module *b) +static int ref_module(struct module *a, struct module *b) { int err; @@ -870,7 +873,6 @@ int ref_module(struct module *a, struct module *b) } return 0; } -EXPORT_SYMBOL_GPL(ref_module); /* Clear the unload stuff of the module. */ static void module_unload_free(struct module *mod) @@ -1059,7 +1061,7 @@ void __symbol_put(const char *symbol) struct module *owner; preempt_disable(); - if (!find_symbol(symbol, &owner, NULL, true, false)) + if (!find_symbol(symbol, &owner, NULL, NULL, true, false)) BUG(); module_put(owner); preempt_enable(); @@ -1151,11 +1153,10 @@ static inline void module_unload_free(struct module *mod) { } -int ref_module(struct module *a, struct module *b) +static int ref_module(struct module *a, struct module *b) { return strong_try_module_get(b); } -EXPORT_SYMBOL_GPL(ref_module); static inline int module_unload_init(struct module *mod) { @@ -1338,7 +1339,7 @@ static inline int check_modstruct_version(const struct load_info *info, * locking is necessary -- use preempt_disable() to placate lockdep. */ preempt_disable(); - if (!find_symbol("module_layout", NULL, &crc, true, false)) { + if (!find_symbol("module_layout", NULL, &crc, NULL, true, false)) { preempt_enable(); BUG(); } @@ -1378,6 +1379,25 @@ static inline int same_magic(const char *amagic, const char *bmagic, } #endif /* CONFIG_MODVERSIONS */ +static bool inherit_taint(struct module *mod, struct module *owner) +{ + if (!owner || !test_bit(TAINT_PROPRIETARY_MODULE, &owner->taints)) + return true; + + if (mod->using_gplonly_symbols) { + pr_err("%s: module using GPL-only symbols uses symbols from proprietary module %s.\n", + mod->name, owner->name); + return false; + } + + if (!test_bit(TAINT_PROPRIETARY_MODULE, &mod->taints)) { + pr_warn("%s: module uses symbols from proprietary module %s, inheriting taint.\n", + mod->name, owner->name); + set_bit(TAINT_PROPRIETARY_MODULE, &mod->taints); + } + return true; +} + /* Resolve a symbol for this module. I.e. if we find one, record usage. */ static const struct kernel_symbol *resolve_symbol(struct module *mod, const struct load_info *info, @@ -1387,6 +1407,7 @@ static const struct kernel_symbol *resolve_symbol(struct module *mod, struct module *owner; const struct kernel_symbol *sym; const s32 *crc; + enum mod_license license; int err; /* @@ -1396,11 +1417,19 @@ static const struct kernel_symbol *resolve_symbol(struct module *mod, */ sched_annotate_sleep(); mutex_lock(&module_mutex); - sym = find_symbol(name, &owner, &crc, + sym = find_symbol(name, &owner, &crc, &license, !(mod->taints & (1 << TAINT_PROPRIETARY_MODULE)), true); if (!sym) goto unlock; + if (license == GPL_ONLY) + mod->using_gplonly_symbols = true; + + if (!inherit_taint(mod, owner)) { + sym = NULL; + goto getname; + } + if (!check_version(info, name, mod, crc)) { sym = ERR_PTR(-EINVAL); goto getname; @@ -2226,7 +2255,7 @@ void *__symbol_get(const char *symbol) const struct kernel_symbol *sym; preempt_disable(); - sym = find_symbol(symbol, &owner, NULL, true, true); + sym = find_symbol(symbol, &owner, NULL, NULL, true, true); if (sym && strong_try_module_get(owner)) sym = NULL; preempt_enable(); @@ -2262,7 +2291,7 @@ static int verify_export_symbols(struct module *mod) for (i = 0; i < ARRAY_SIZE(arr); i++) { for (s = arr[i].sym; s < arr[i].sym + arr[i].num; s++) { if (find_symbol(kernel_symbol_name(s), &owner, NULL, - true, false)) { + NULL, true, false)) { pr_err("%s: exports duplicate symbol %s" " (owned by %s)\n", mod->name, kernel_symbol_name(s), @@ -4385,7 +4414,6 @@ struct module *__module_address(unsigned long addr) } return mod; } -EXPORT_SYMBOL_GPL(__module_address); /* * is_module_text_address - is this address inside module code? @@ -4424,7 +4452,6 @@ struct module *__module_text_address(unsigned long addr) } return mod; } -EXPORT_SYMBOL_GPL(__module_text_address); /* Don't grab lock, we're oopsing. */ void print_modules(void) diff --git a/kernel/sched/debug.c b/kernel/sched/debug.c index 78fadf0438ea0..9518606fa1e58 100644 --- a/kernel/sched/debug.c +++ b/kernel/sched/debug.c @@ -11,8 +11,6 @@ */ #include "sched.h" -static DEFINE_SPINLOCK(sched_debug_lock); - /* * This allows printing both to /proc/sched_debug and * to the console @@ -434,16 +432,37 @@ static void print_cfs_group_stats(struct seq_file *m, int cpu, struct task_group #endif #ifdef CONFIG_CGROUP_SCHED +static DEFINE_SPINLOCK(sched_debug_lock); static char group_path[PATH_MAX]; -static char *task_group_path(struct task_group *tg) +static void task_group_path(struct task_group *tg, char *path, int plen) { - if (autogroup_path(tg, group_path, PATH_MAX)) - return group_path; + if (autogroup_path(tg, path, plen)) + return; - cgroup_path(tg->css.cgroup, group_path, PATH_MAX); + cgroup_path(tg->css.cgroup, path, plen); +} - return group_path; +/* + * Only 1 SEQ_printf_task_group_path() caller can use the full length + * group_path[] for cgroup path. Other simultaneous callers will have + * to use a shorter stack buffer. A "..." suffix is appended at the end + * of the stack buffer so that it will show up in case the output length + * matches the given buffer size to indicate possible path name truncation. + */ +#define SEQ_printf_task_group_path(m, tg, fmt...) \ +{ \ + if (spin_trylock(&sched_debug_lock)) { \ + task_group_path(tg, group_path, sizeof(group_path)); \ + SEQ_printf(m, fmt, group_path); \ + spin_unlock(&sched_debug_lock); \ + } else { \ + char buf[128]; \ + char *bufend = buf + sizeof(buf) - 3; \ + task_group_path(tg, buf, bufend - buf); \ + strcpy(bufend - 1, "..."); \ + SEQ_printf(m, fmt, buf); \ + } \ } #endif @@ -470,7 +489,7 @@ print_task(struct seq_file *m, struct rq *rq, struct task_struct *p) SEQ_printf(m, " %d %d", task_node(p), task_numa_group_id(p)); #endif #ifdef CONFIG_CGROUP_SCHED - SEQ_printf(m, " %s", task_group_path(task_group(p))); + SEQ_printf_task_group_path(m, task_group(p), " %s") #endif SEQ_printf(m, "\n"); @@ -507,7 +526,7 @@ void print_cfs_rq(struct seq_file *m, int cpu, struct cfs_rq *cfs_rq) #ifdef CONFIG_FAIR_GROUP_SCHED SEQ_printf(m, "\n"); - SEQ_printf(m, "cfs_rq[%d]:%s\n", cpu, task_group_path(cfs_rq->tg)); + SEQ_printf_task_group_path(m, cfs_rq->tg, "cfs_rq[%d]:%s\n", cpu); #else SEQ_printf(m, "\n"); SEQ_printf(m, "cfs_rq[%d]:\n", cpu); @@ -579,7 +598,7 @@ void print_rt_rq(struct seq_file *m, int cpu, struct rt_rq *rt_rq) { #ifdef CONFIG_RT_GROUP_SCHED SEQ_printf(m, "\n"); - SEQ_printf(m, "rt_rq[%d]:%s\n", cpu, task_group_path(rt_rq->tg)); + SEQ_printf_task_group_path(m, rt_rq->tg, "rt_rq[%d]:%s\n", cpu); #else SEQ_printf(m, "\n"); SEQ_printf(m, "rt_rq[%d]:\n", cpu); @@ -631,7 +650,6 @@ void print_dl_rq(struct seq_file *m, int cpu, struct dl_rq *dl_rq) static void print_cpu(struct seq_file *m, int cpu) { struct rq *rq = cpu_rq(cpu); - unsigned long flags; #ifdef CONFIG_X86 { @@ -690,13 +708,11 @@ do { \ } #undef P - spin_lock_irqsave(&sched_debug_lock, flags); print_cfs_stats(m, cpu); print_rt_stats(m, cpu); print_dl_stats(m, cpu); print_rq(m, rq, cpu); - spin_unlock_irqrestore(&sched_debug_lock, flags); SEQ_printf(m, "\n"); } diff --git a/kernel/sched/fair.c b/kernel/sched/fair.c index 696d08a4593ef..80392cdd5f3b2 100644 --- a/kernel/sched/fair.c +++ b/kernel/sched/fair.c @@ -9903,16 +9903,22 @@ static void propagate_entity_cfs_rq(struct sched_entity *se) { struct cfs_rq *cfs_rq; + list_add_leaf_cfs_rq(cfs_rq_of(se)); + /* Start to propagate at parent */ se = se->parent; for_each_sched_entity(se) { cfs_rq = cfs_rq_of(se); - if (cfs_rq_throttled(cfs_rq)) - break; + if (!cfs_rq_throttled(cfs_rq)){ + update_load_avg(cfs_rq, se, UPDATE_TG); + list_add_leaf_cfs_rq(cfs_rq); + continue; + } - update_load_avg(cfs_rq, se, UPDATE_TG); + if (list_add_leaf_cfs_rq(cfs_rq)) + break; } } #else diff --git a/kernel/smp.c b/kernel/smp.c index 084c8b3a26812..00d208ef07c76 100644 --- a/kernel/smp.c +++ b/kernel/smp.c @@ -103,12 +103,12 @@ void __init call_function_init(void) * previous function call. For multi-cpu calls its even more interesting * as we'll have to ensure no other cpu is observing our csd. */ -static __always_inline void csd_lock_wait(call_single_data_t *csd) +static __always_inline void csd_lock_wait(struct __call_single_data *csd) { smp_cond_load_acquire(&csd->flags, !(VAL & CSD_FLAG_LOCK)); } -static __always_inline void csd_lock(call_single_data_t *csd) +static __always_inline void csd_lock(struct __call_single_data *csd) { csd_lock_wait(csd); csd->flags |= CSD_FLAG_LOCK; @@ -121,7 +121,7 @@ static __always_inline void csd_lock(call_single_data_t *csd) smp_wmb(); } -static __always_inline void csd_unlock(call_single_data_t *csd) +static __always_inline void csd_unlock(struct __call_single_data *csd) { WARN_ON(!(csd->flags & CSD_FLAG_LOCK)); @@ -138,7 +138,7 @@ static DEFINE_PER_CPU_SHARED_ALIGNED(call_single_data_t, csd_data); * for execution on the given CPU. data must already have * ->func, ->info, and ->flags set. */ -static int generic_exec_single(int cpu, call_single_data_t *csd, +static int generic_exec_single(int cpu, struct __call_single_data *csd, smp_call_func_t func, void *info) { if (cpu == smp_processor_id()) { @@ -323,7 +323,7 @@ EXPORT_SYMBOL(smp_call_function_single); * NOTE: Be careful, there is unfortunately no current debugging facility to * validate the correctness of this serialization. */ -int smp_call_function_single_async(int cpu, call_single_data_t *csd) +int smp_call_function_single_async(int cpu, struct __call_single_data *csd) { int err = 0; diff --git a/kernel/time/posix-timers.c b/kernel/time/posix-timers.c index 5a01c4fdbfef4..48758108e055c 100644 --- a/kernel/time/posix-timers.c +++ b/kernel/time/posix-timers.c @@ -1166,8 +1166,8 @@ COMPAT_SYSCALL_DEFINE2(clock_adjtime, clockid_t, which_clock, err = kc->clock_adj(which_clock, &ktx); - if (err >= 0) - err = compat_put_timex(utp, &ktx); + if (err >= 0 && compat_put_timex(utp, &ktx)) + return -EFAULT; return err; } diff --git a/kernel/trace/ftrace.c b/kernel/trace/ftrace.c index 3492202762c73..f8d82b36dd668 100644 --- a/kernel/trace/ftrace.c +++ b/kernel/trace/ftrace.c @@ -5023,7 +5023,10 @@ int ftrace_regex_release(struct inode *inode, struct file *file) parser = &iter->parser; if (trace_parser_loaded(parser)) { - ftrace_match_records(iter->hash, parser->buffer, parser->idx); + int enable = !(iter->flags & FTRACE_ITER_NOTRACE); + + ftrace_process_regex(iter, parser->buffer, + parser->idx, enable); } trace_parser_put(parser); diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c index bca0b6df53caf..4eea58a907f08 100644 --- a/kernel/trace/trace.c +++ b/kernel/trace/trace.c @@ -1935,14 +1935,13 @@ static void tracing_stop_tr(struct trace_array *tr) static int trace_save_cmdline(struct task_struct *tsk) { - unsigned pid, idx; + unsigned tpid, idx; /* treat recording of idle task as a success */ if (!tsk->pid) return 1; - if (unlikely(tsk->pid > PID_MAX_DEFAULT)) - return 0; + tpid = tsk->pid & (PID_MAX_DEFAULT - 1); /* * It's not the end of the world if we don't get @@ -1953,26 +1952,15 @@ static int trace_save_cmdline(struct task_struct *tsk) if (!arch_spin_trylock(&trace_cmdline_lock)) return 0; - idx = savedcmd->map_pid_to_cmdline[tsk->pid]; + idx = savedcmd->map_pid_to_cmdline[tpid]; if (idx == NO_CMDLINE_MAP) { idx = (savedcmd->cmdline_idx + 1) % savedcmd->cmdline_num; - /* - * Check whether the cmdline buffer at idx has a pid - * mapped. We are going to overwrite that entry so we - * need to clear the map_pid_to_cmdline. Otherwise we - * would read the new comm for the old pid. - */ - pid = savedcmd->map_cmdline_to_pid[idx]; - if (pid != NO_CMDLINE_MAP) - savedcmd->map_pid_to_cmdline[pid] = NO_CMDLINE_MAP; - - savedcmd->map_cmdline_to_pid[idx] = tsk->pid; - savedcmd->map_pid_to_cmdline[tsk->pid] = idx; - + savedcmd->map_pid_to_cmdline[tpid] = idx; savedcmd->cmdline_idx = idx; } + savedcmd->map_cmdline_to_pid[idx] = tsk->pid; set_cmdline(idx, tsk->comm); arch_spin_unlock(&trace_cmdline_lock); @@ -1983,6 +1971,7 @@ static int trace_save_cmdline(struct task_struct *tsk) static void __trace_find_cmdline(int pid, char comm[]) { unsigned map; + int tpid; if (!pid) { strcpy(comm, ""); @@ -1994,16 +1983,16 @@ static void __trace_find_cmdline(int pid, char comm[]) return; } - if (pid > PID_MAX_DEFAULT) { - strcpy(comm, "<...>"); - return; + tpid = pid & (PID_MAX_DEFAULT - 1); + map = savedcmd->map_pid_to_cmdline[tpid]; + if (map != NO_CMDLINE_MAP) { + tpid = savedcmd->map_cmdline_to_pid[map]; + if (tpid == pid) { + strlcpy(comm, get_saved_cmdlines(map), TASK_COMM_LEN); + return; + } } - - map = savedcmd->map_pid_to_cmdline[pid]; - if (map != NO_CMDLINE_MAP) - strlcpy(comm, get_saved_cmdlines(map), TASK_COMM_LEN); - else - strcpy(comm, "<...>"); + strcpy(comm, "<...>"); } void trace_find_cmdline(int pid, char comm[]) diff --git a/kernel/trace/trace_clock.c b/kernel/trace/trace_clock.c index aaf6793ededaa..c1637f90c8a38 100644 --- a/kernel/trace/trace_clock.c +++ b/kernel/trace/trace_clock.c @@ -95,33 +95,49 @@ u64 notrace trace_clock_global(void) { unsigned long flags; int this_cpu; - u64 now; + u64 now, prev_time; raw_local_irq_save(flags); this_cpu = raw_smp_processor_id(); - now = sched_clock_cpu(this_cpu); + /* - * If in an NMI context then dont risk lockups and return the - * cpu_clock() time: + * The global clock "guarantees" that the events are ordered + * between CPUs. But if two events on two different CPUS call + * trace_clock_global at roughly the same time, it really does + * not matter which one gets the earlier time. Just make sure + * that the same CPU will always show a monotonic clock. + * + * Use a read memory barrier to get the latest written + * time that was recorded. */ - if (unlikely(in_nmi())) - goto out; + smp_rmb(); + prev_time = READ_ONCE(trace_clock_struct.prev_time); + now = sched_clock_cpu(this_cpu); - arch_spin_lock(&trace_clock_struct.lock); + /* Make sure that now is always greater than prev_time */ + if ((s64)(now - prev_time) < 0) + now = prev_time + 1; /* - * TODO: if this happens often then maybe we should reset - * my_scd->clock to prev_time+1, to make sure - * we start ticking with the local clock from now on? + * If in an NMI context then dont risk lockups and simply return + * the current time. */ - if ((s64)(now - trace_clock_struct.prev_time) < 0) - now = trace_clock_struct.prev_time + 1; + if (unlikely(in_nmi())) + goto out; - trace_clock_struct.prev_time = now; + /* Tracing can cause strange recursion, always use a try lock */ + if (arch_spin_trylock(&trace_clock_struct.lock)) { + /* Reread prev_time in case it was already updated */ + prev_time = READ_ONCE(trace_clock_struct.prev_time); + if ((s64)(now - prev_time) < 0) + now = prev_time + 1; - arch_spin_unlock(&trace_clock_struct.lock); + trace_clock_struct.prev_time = now; + /* The unlock acts as the wmb for the above rmb */ + arch_spin_unlock(&trace_clock_struct.lock); + } out: raw_local_irq_restore(flags); diff --git a/kernel/up.c b/kernel/up.c index 42c46bf3e0a5c..2080f75e0e65c 100644 --- a/kernel/up.c +++ b/kernel/up.c @@ -23,7 +23,7 @@ int smp_call_function_single(int cpu, void (*func) (void *info), void *info, } EXPORT_SYMBOL(smp_call_function_single); -int smp_call_function_single_async(int cpu, call_single_data_t *csd) +int smp_call_function_single_async(int cpu, struct __call_single_data *csd) { unsigned long flags; diff --git a/lib/bug.c b/lib/bug.c index 1077366f496ba..f4fcac5dd766f 100644 --- a/lib/bug.c +++ b/lib/bug.c @@ -155,30 +155,27 @@ enum bug_trap_type report_bug(unsigned long bugaddr, struct pt_regs *regs) file = NULL; line = 0; - warning = 0; - if (bug) { #ifdef CONFIG_DEBUG_BUGVERBOSE #ifndef CONFIG_GENERIC_BUG_RELATIVE_POINTERS - file = bug->file; + file = bug->file; #else - file = (const char *)bug + bug->file_disp; + file = (const char *)bug + bug->file_disp; #endif - line = bug->line; + line = bug->line; #endif - warning = (bug->flags & BUGFLAG_WARNING) != 0; - once = (bug->flags & BUGFLAG_ONCE) != 0; - done = (bug->flags & BUGFLAG_DONE) != 0; - - if (warning && once) { - if (done) - return BUG_TRAP_TYPE_WARN; - - /* - * Since this is the only store, concurrency is not an issue. - */ - bug->flags |= BUGFLAG_DONE; - } + warning = (bug->flags & BUGFLAG_WARNING) != 0; + once = (bug->flags & BUGFLAG_ONCE) != 0; + done = (bug->flags & BUGFLAG_DONE) != 0; + + if (warning && once) { + if (done) + return BUG_TRAP_TYPE_WARN; + + /* + * Since this is the only store, concurrency is not an issue. + */ + bug->flags |= BUGFLAG_DONE; } if (warning) { diff --git a/lib/kobject_uevent.c b/lib/kobject_uevent.c index 7761f32943391..26d21339bef27 100644 --- a/lib/kobject_uevent.c +++ b/lib/kobject_uevent.c @@ -250,12 +250,13 @@ static int kobj_usermode_filter(struct kobject *kobj) static int init_uevent_argv(struct kobj_uevent_env *env, const char *subsystem) { + int buffer_size = sizeof(env->buf) - env->buflen; int len; - len = strlcpy(&env->buf[env->buflen], subsystem, - sizeof(env->buf) - env->buflen); - if (len >= (sizeof(env->buf) - env->buflen)) { - WARN(1, KERN_ERR "init_uevent_argv: buffer size too small\n"); + len = strlcpy(&env->buf[env->buflen], subsystem, buffer_size); + if (len >= buffer_size) { + pr_warn("init_uevent_argv: buffer size of %d too small, needed %d\n", + buffer_size, len); return -ENOMEM; } diff --git a/lib/nlattr.c b/lib/nlattr.c index e335bcafa9e4c..00bfc6aece055 100644 --- a/lib/nlattr.c +++ b/lib/nlattr.c @@ -402,7 +402,7 @@ int nla_strcmp(const struct nlattr *nla, const char *str) int attrlen = nla_len(nla); int d; - if (attrlen > 0 && buf[attrlen - 1] == '\0') + while (attrlen > 0 && buf[attrlen - 1] == '\0') attrlen--; d = attrlen - len; diff --git a/lib/stackdepot.c b/lib/stackdepot.c index 3376a32911864..d0f1b7d0ce2e7 100644 --- a/lib/stackdepot.c +++ b/lib/stackdepot.c @@ -78,7 +78,7 @@ static void *stack_slabs[STACK_ALLOC_MAX_SLABS]; static int depot_index; static int next_slab_inited; static size_t depot_offset; -static DEFINE_SPINLOCK(depot_lock); +static DEFINE_RAW_SPINLOCK(depot_lock); static bool init_stack_slab(void **prealloc) { @@ -266,7 +266,7 @@ depot_stack_handle_t depot_save_stack(struct stack_trace *trace, prealloc = page_address(page); } - spin_lock_irqsave(&depot_lock, flags); + raw_spin_lock_irqsave(&depot_lock, flags); found = find_stack(*bucket, trace->entries, trace->nr_entries, hash); if (!found) { @@ -290,7 +290,7 @@ depot_stack_handle_t depot_save_stack(struct stack_trace *trace, WARN_ON(!init_stack_slab(&prealloc)); } - spin_unlock_irqrestore(&depot_lock, flags); + raw_spin_unlock_irqrestore(&depot_lock, flags); exit: if (prealloc) { /* Nobody used this memory, ok to free it. */ diff --git a/mm/hugetlb.c b/mm/hugetlb.c index f37a821dc5ce2..1dfaec50ff933 100644 --- a/mm/hugetlb.c +++ b/mm/hugetlb.c @@ -588,13 +588,20 @@ void hugetlb_fix_reserve_counts(struct inode *inode) { struct hugepage_subpool *spool = subpool_inode(inode); long rsv_adjust; + bool reserved = false; rsv_adjust = hugepage_subpool_get_pages(spool, 1); - if (rsv_adjust) { + if (rsv_adjust > 0) { struct hstate *h = hstate_inode(inode); - hugetlb_acct_memory(h, 1); + if (!hugetlb_acct_memory(h, 1)) + reserved = true; + } else if (!rsv_adjust) { + reserved = true; } + + if (!reserved) + pr_warn("hugetlb: Huge Page Reserved count may go negative.\n"); } /* diff --git a/mm/khugepaged.c b/mm/khugepaged.c index 9c7dc2276156b..5dd14ef2e1de8 100644 --- a/mm/khugepaged.c +++ b/mm/khugepaged.c @@ -616,17 +616,17 @@ static int __collapse_huge_page_isolate(struct vm_area_struct *vma, mmu_notifier_test_young(vma->vm_mm, address)) referenced++; } - if (likely(writable)) { - if (likely(referenced)) { - result = SCAN_SUCCEED; - trace_mm_collapse_huge_page_isolate(page, none_or_zero, - referenced, writable, result); - return 1; - } - } else { + + if (unlikely(!writable)) { result = SCAN_PAGE_RO; + } else if (unlikely(!referenced)) { + result = SCAN_LACK_REFERENCED_PAGE; + } else { + result = SCAN_SUCCEED; + trace_mm_collapse_huge_page_isolate(page, none_or_zero, + referenced, writable, result); + return 1; } - out: release_pte_pages(pte, _pte); trace_mm_collapse_huge_page_isolate(page, none_or_zero, diff --git a/mm/ksm.c b/mm/ksm.c index d021bcf94c41d..87a541ab1474f 100644 --- a/mm/ksm.c +++ b/mm/ksm.c @@ -778,6 +778,7 @@ static void remove_rmap_item_from_tree(struct rmap_item *rmap_item) stable_node->rmap_hlist_len--; put_anon_vma(rmap_item->anon_vma); + rmap_item->head = NULL; rmap_item->address &= PAGE_MASK; } else if (rmap_item->address & UNSTABLE_FLAG) { diff --git a/mm/memory-failure.c b/mm/memory-failure.c index 148fdd929a195..034607a68ccb3 100644 --- a/mm/memory-failure.c +++ b/mm/memory-failure.c @@ -1220,7 +1220,7 @@ static int memory_failure_dev_pagemap(unsigned long pfn, int flags, * communicated in siginfo, see kill_proc() */ start = (page->index << PAGE_SHIFT) & ~(size - 1); - unmap_mapping_range(page->mapping, start, start + size, 0); + unmap_mapping_range(page->mapping, start, size, 0); } kill_procs(&tokill, flags & MF_MUST_KILL, !unmap_success, pfn, flags); rc = 0; diff --git a/mm/shmem.c b/mm/shmem.c index dea5120565d30..9fd0e72757cfa 100644 --- a/mm/shmem.c +++ b/mm/shmem.c @@ -2271,8 +2271,18 @@ static int shmem_mfill_atomic_pte(struct mm_struct *dst_mm, pgoff_t offset, max_off; ret = -ENOMEM; - if (!shmem_inode_acct_block(inode, 1)) + if (!shmem_inode_acct_block(inode, 1)) { + /* + * We may have got a page, returned -ENOENT triggering a retry, + * and now we find ourselves with -ENOMEM. Release the page, to + * avoid a BUG_ON in our caller. + */ + if (unlikely(*pagep)) { + put_page(*pagep); + *pagep = NULL; + } goto out; + } if (!*pagep) { page = shmem_alloc_page(gfp, info, pgoff); diff --git a/mm/sparse.c b/mm/sparse.c index 3b24ba903d9ee..ed60f0a375fec 100644 --- a/mm/sparse.c +++ b/mm/sparse.c @@ -467,6 +467,7 @@ static void __init sparse_init_nid(int nid, unsigned long pnum_begin, pr_err("%s: node[%d] memory map backing failed. Some memory will not be available.", __func__, nid); pnum_begin = pnum; + sparse_buffer_fini(); goto failed; } check_usemap_section_nr(nid, usemap); diff --git a/net/bluetooth/ecdh_helper.h b/net/bluetooth/ecdh_helper.h index a6f8d03d4aaf6..830723971cf83 100644 --- a/net/bluetooth/ecdh_helper.h +++ b/net/bluetooth/ecdh_helper.h @@ -25,6 +25,6 @@ int compute_ecdh_secret(struct crypto_kpp *tfm, const u8 pair_public_key[64], u8 secret[32]); -int set_ecdh_privkey(struct crypto_kpp *tfm, const u8 *private_key); +int set_ecdh_privkey(struct crypto_kpp *tfm, const u8 private_key[32]); int generate_ecdh_public_key(struct crypto_kpp *tfm, u8 public_key[64]); int generate_ecdh_keys(struct crypto_kpp *tfm, u8 public_key[64]); diff --git a/net/bluetooth/hci_event.c b/net/bluetooth/hci_event.c index b58afd2d5ebf4..2e2cad58b6ccf 100644 --- a/net/bluetooth/hci_event.c +++ b/net/bluetooth/hci_event.c @@ -4721,6 +4721,7 @@ static void hci_loglink_complete_evt(struct hci_dev *hdev, struct sk_buff *skb) return; hchan->handle = le16_to_cpu(ev->handle); + hchan->amp = true; BT_DBG("hcon %p mgr %p hchan %p", hcon, hcon->amp_mgr, hchan); @@ -4753,7 +4754,7 @@ static void hci_disconn_loglink_complete_evt(struct hci_dev *hdev, hci_dev_lock(hdev); hchan = hci_chan_lookup_handle(hdev, le16_to_cpu(ev->handle)); - if (!hchan) + if (!hchan || !hchan->amp) goto unlock; amp_destroy_logical_link(hchan, ev->reason); diff --git a/net/bluetooth/hci_request.c b/net/bluetooth/hci_request.c index a8ddd211e94c2..76bd6b1227240 100644 --- a/net/bluetooth/hci_request.c +++ b/net/bluetooth/hci_request.c @@ -271,12 +271,16 @@ int hci_req_sync(struct hci_dev *hdev, int (*req)(struct hci_request *req, { int ret; - if (!test_bit(HCI_UP, &hdev->flags)) - return -ENETDOWN; - /* Serialize all requests */ hci_req_sync_lock(hdev); - ret = __hci_req_sync(hdev, req, opt, timeout, hci_status); + /* check the state after obtaing the lock to protect the HCI_UP + * against any races from hci_dev_do_close when the controller + * gets removed. + */ + if (test_bit(HCI_UP, &hdev->flags)) + ret = __hci_req_sync(hdev, req, opt, timeout, hci_status); + else + ret = -ENETDOWN; hci_req_sync_unlock(hdev); return ret; diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c index f1ff833210231..c0d64b4144d4a 100644 --- a/net/bluetooth/l2cap_core.c +++ b/net/bluetooth/l2cap_core.c @@ -445,6 +445,8 @@ struct l2cap_chan *l2cap_chan_create(void) if (!chan) return NULL; + skb_queue_head_init(&chan->tx_q); + skb_queue_head_init(&chan->srej_q); mutex_init(&chan->lock); /* Set default lock nesting level */ @@ -510,7 +512,9 @@ void l2cap_chan_set_defaults(struct l2cap_chan *chan) chan->flush_to = L2CAP_DEFAULT_FLUSH_TO; chan->retrans_timeout = L2CAP_DEFAULT_RETRANS_TO; chan->monitor_timeout = L2CAP_DEFAULT_MONITOR_TO; + chan->conf_state = 0; + set_bit(CONF_NOT_COMPLETE, &chan->conf_state); set_bit(FLAG_FORCE_ACTIVE, &chan->flags); } diff --git a/net/bluetooth/l2cap_sock.c b/net/bluetooth/l2cap_sock.c index 198a1fdd6709e..967a9bb144157 100644 --- a/net/bluetooth/l2cap_sock.c +++ b/net/bluetooth/l2cap_sock.c @@ -179,9 +179,17 @@ static int l2cap_sock_connect(struct socket *sock, struct sockaddr *addr, struct l2cap_chan *chan = l2cap_pi(sk)->chan; struct sockaddr_l2 la; int len, err = 0; + bool zapped; BT_DBG("sk %p", sk); + lock_sock(sk); + zapped = sock_flag(sk, SOCK_ZAPPED); + release_sock(sk); + + if (zapped) + return -EINVAL; + if (!addr || alen < offsetofend(struct sockaddr, sa_family) || addr->sa_family != AF_BLUETOOTH) return -EINVAL; diff --git a/net/bridge/br_arp_nd_proxy.c b/net/bridge/br_arp_nd_proxy.c index eb44ae05abaaf..b52e703622682 100644 --- a/net/bridge/br_arp_nd_proxy.c +++ b/net/bridge/br_arp_nd_proxy.c @@ -158,7 +158,9 @@ void br_do_proxy_suppress_arp(struct sk_buff *skb, struct net_bridge *br, if (br->neigh_suppress_enabled) { if (p && (p->flags & BR_NEIGH_SUPPRESS)) return; - if (ipv4_is_zeronet(sip) || sip == tip) { + if (parp->ar_op != htons(ARPOP_RREQUEST) && + parp->ar_op != htons(ARPOP_RREPLY) && + (ipv4_is_zeronet(sip) || sip == tip)) { /* prevent flooding to neigh suppress ports */ BR_INPUT_SKB_CB(skb)->proxyarp_replied = true; return; diff --git a/net/core/ethtool.c b/net/core/ethtool.c index 1011625a0ca4b..83028017c26dd 100644 --- a/net/core/ethtool.c +++ b/net/core/ethtool.c @@ -618,7 +618,7 @@ store_link_ksettings_for_user(void __user *to, { struct ethtool_link_usettings link_usettings; - memcpy(&link_usettings.base, &from->base, sizeof(link_usettings)); + memcpy(&link_usettings, from, sizeof(link_usettings)); bitmap_to_arr32(link_usettings.link_modes.supported, from->link_modes.supported, __ETHTOOL_LINK_MODE_MASK_NBITS); diff --git a/net/hsr/hsr_framereg.c b/net/hsr/hsr_framereg.c index f5a3601948ca0..37795502bb511 100644 --- a/net/hsr/hsr_framereg.c +++ b/net/hsr/hsr_framereg.c @@ -310,7 +310,8 @@ void hsr_addr_subst_dest(struct hsr_node *node_src, struct sk_buff *skb, node_dst = find_node_by_AddrA(&port->hsr->node_db, eth_hdr(skb)->h_dest); if (!node_dst) { - WARN_ONCE(1, "%s: Unknown node\n", __func__); + if (net_ratelimit()) + netdev_err(skb->dev, "%s: Unknown node\n", __func__); return; } if (port->type != node_dst->AddrB_port) diff --git a/net/ipv4/tcp_cong.c b/net/ipv4/tcp_cong.c index 00a7482b6fbd9..533f8d84d2f71 100644 --- a/net/ipv4/tcp_cong.c +++ b/net/ipv4/tcp_cong.c @@ -228,6 +228,10 @@ int tcp_set_default_congestion_control(struct net *net, const char *name) ret = -ENOENT; } else if (!try_module_get(ca->owner)) { ret = -EBUSY; + } else if (!net_eq(net, &init_net) && + !(ca->flags & TCP_CONG_NON_RESTRICTED)) { + /* Only init netns can set default to a restricted algorithm */ + ret = -EPERM; } else { prev = xchg(&net->ipv4.tcp_congestion_control, ca); if (prev) diff --git a/net/ipv6/ip6_gre.c b/net/ipv6/ip6_gre.c index 86c8ea7d70067..043e57d08a3e9 100644 --- a/net/ipv6/ip6_gre.c +++ b/net/ipv6/ip6_gre.c @@ -392,7 +392,6 @@ static struct ip6_tnl *ip6gre_tunnel_locate(struct net *net, if (!(nt->parms.o_flags & TUNNEL_SEQ)) dev->features |= NETIF_F_LLTX; - dev_hold(dev); ip6gre_tunnel_link(ign, nt); return nt; @@ -1503,6 +1502,7 @@ static int ip6gre_tunnel_init_common(struct net_device *dev) } ip6gre_tnl_init_features(dev); + dev_hold(dev); return 0; cleanup_dst_cache_init: @@ -1545,8 +1545,6 @@ static void ip6gre_fb_tunnel_init(struct net_device *dev) strcpy(tunnel->parms.name, dev->name); tunnel->hlen = sizeof(struct ipv6hdr) + 4; - - dev_hold(dev); } static struct inet6_protocol ip6gre_protocol __read_mostly = { @@ -1896,6 +1894,7 @@ static int ip6erspan_tap_init(struct net_device *dev) dev->priv_flags |= IFF_LIVE_ADDR_CHANGE; ip6erspan_tnl_link_config(tunnel, 1); + dev_hold(dev); return 0; cleanup_dst_cache_init: @@ -2001,8 +2000,6 @@ static int ip6gre_newlink_common(struct net *src_net, struct net_device *dev, if (tb[IFLA_MTU]) ip6_tnl_change_mtu(dev, nla_get_u32(tb[IFLA_MTU])); - dev_hold(dev); - out: return err; } diff --git a/net/ipv6/ip6_tunnel.c b/net/ipv6/ip6_tunnel.c index 28c4a693ab98d..35c127c3eee78 100644 --- a/net/ipv6/ip6_tunnel.c +++ b/net/ipv6/ip6_tunnel.c @@ -272,7 +272,6 @@ static int ip6_tnl_create2(struct net_device *dev) strcpy(t->parms.name, dev->name); - dev_hold(dev); ip6_tnl_link(ip6n, t); return 0; @@ -1866,6 +1865,7 @@ ip6_tnl_dev_init_gen(struct net_device *dev) dev->min_mtu = ETH_MIN_MTU; dev->max_mtu = IP6_MAX_MTU - dev->hard_header_len; + dev_hold(dev); return 0; destroy_dst: @@ -1909,7 +1909,6 @@ static int __net_init ip6_fb_tnl_dev_init(struct net_device *dev) struct ip6_tnl_net *ip6n = net_generic(net, ip6_tnl_net_id); t->parms.proto = IPPROTO_IPV6; - dev_hold(dev); rcu_assign_pointer(ip6n->tnls_wc[0], t); return 0; diff --git a/net/ipv6/ip6_vti.c b/net/ipv6/ip6_vti.c index 94f16e82a4581..290badfe70e06 100644 --- a/net/ipv6/ip6_vti.c +++ b/net/ipv6/ip6_vti.c @@ -196,7 +196,6 @@ static int vti6_tnl_create2(struct net_device *dev) strcpy(t->parms.name, dev->name); - dev_hold(dev); vti6_tnl_link(ip6n, t); return 0; @@ -925,6 +924,7 @@ static inline int vti6_dev_init_gen(struct net_device *dev) dev->tstats = netdev_alloc_pcpu_stats(struct pcpu_sw_netstats); if (!dev->tstats) return -ENOMEM; + dev_hold(dev); return 0; } @@ -956,7 +956,6 @@ static int __net_init vti6_fb_tnl_dev_init(struct net_device *dev) struct vti6_net *ip6n = net_generic(net, vti6_net_id); t->parms.proto = IPPROTO_IPV6; - dev_hold(dev); rcu_assign_pointer(ip6n->tnls_wc[0], t); return 0; diff --git a/net/ipv6/sit.c b/net/ipv6/sit.c index ad737b68b8e96..4a49200d0d11c 100644 --- a/net/ipv6/sit.c +++ b/net/ipv6/sit.c @@ -215,8 +215,6 @@ static int ipip6_tunnel_create(struct net_device *dev) ipip6_tunnel_clone_6rd(dev, sitn); - dev_hold(dev); - ipip6_tunnel_link(sitn, t); return 0; @@ -1407,7 +1405,7 @@ static int ipip6_tunnel_init(struct net_device *dev) dev->tstats = NULL; return err; } - + dev_hold(dev); return 0; } @@ -1423,7 +1421,6 @@ static void __net_init ipip6_fb_tunnel_init(struct net_device *dev) iph->ihl = 5; iph->ttl = 64; - dev_hold(dev); rcu_assign_pointer(sitn->tunnels_wc[0], tunnel); } diff --git a/net/mac80211/main.c b/net/mac80211/main.c index f44d00f35fe7b..e8c4e9c0c5a09 100644 --- a/net/mac80211/main.c +++ b/net/mac80211/main.c @@ -1080,8 +1080,11 @@ int ieee80211_register_hw(struct ieee80211_hw *hw) if (local->hw.wiphy->max_scan_ie_len) local->hw.wiphy->max_scan_ie_len -= local->scan_ies_len; - WARN_ON(!ieee80211_cs_list_valid(local->hw.cipher_schemes, - local->hw.n_cipher_schemes)); + if (WARN_ON(!ieee80211_cs_list_valid(local->hw.cipher_schemes, + local->hw.n_cipher_schemes))) { + result = -EINVAL; + goto fail_workqueue; + } result = ieee80211_init_cipher_suites(local); if (result < 0) diff --git a/net/mac80211/mlme.c b/net/mac80211/mlme.c index c53a332f7d65a..cbcb60face2c5 100644 --- a/net/mac80211/mlme.c +++ b/net/mac80211/mlme.c @@ -1185,6 +1185,11 @@ static void ieee80211_chswitch_post_beacon(struct ieee80211_sub_if_data *sdata) sdata->vif.csa_active = false; ifmgd->csa_waiting_bcn = false; + /* + * If the CSA IE is still present on the beacon after the switch, + * we need to consider it as a new CSA (possibly to self). + */ + ifmgd->beacon_crc_valid = false; ret = drv_post_channel_switch(sdata); if (ret) { diff --git a/net/netfilter/nf_conntrack_standalone.c b/net/netfilter/nf_conntrack_standalone.c index 2e3ae494f3697..da0c9fa381d20 100644 --- a/net/netfilter/nf_conntrack_standalone.c +++ b/net/netfilter/nf_conntrack_standalone.c @@ -594,8 +594,11 @@ static int nf_conntrack_standalone_init_sysctl(struct net *net) if (net->user_ns != &init_user_ns) table[0].procname = NULL; - if (!net_eq(&init_net, net)) + if (!net_eq(&init_net, net)) { + table[0].mode = 0444; table[2].mode = 0444; + table[5].mode = 0444; + } net->ct.sysctl_header = register_net_sysctl(net, "net/netfilter", table); if (!net->ct.sysctl_header) diff --git a/net/netfilter/nfnetlink_osf.c b/net/netfilter/nfnetlink_osf.c index 131f9f8c0b092..917f06110c823 100644 --- a/net/netfilter/nfnetlink_osf.c +++ b/net/netfilter/nfnetlink_osf.c @@ -191,6 +191,8 @@ static const struct tcphdr *nf_osf_hdr_ctx_init(struct nf_osf_hdr_ctx *ctx, ctx->optp = skb_header_pointer(skb, ip_hdrlen(skb) + sizeof(struct tcphdr), ctx->optsize, opts); + if (!ctx->optp) + return NULL; } return tcp; diff --git a/net/netfilter/nft_set_hash.c b/net/netfilter/nft_set_hash.c index 05118e03c3e48..dbc4ed643b4bc 100644 --- a/net/netfilter/nft_set_hash.c +++ b/net/netfilter/nft_set_hash.c @@ -392,9 +392,17 @@ static void nft_rhash_destroy(const struct nft_set *set) (void *)set); } +/* Number of buckets is stored in u32, so cap our result to 1U<<31 */ +#define NFT_MAX_BUCKETS (1U << 31) + static u32 nft_hash_buckets(u32 size) { - return roundup_pow_of_two(size * 4 / 3); + u64 val = div_u64((u64)size * 4, 3); + + if (val >= NFT_MAX_BUCKETS) + return NFT_MAX_BUCKETS; + + return roundup_pow_of_two(val); } static bool nft_rhash_estimate(const struct nft_set_desc *desc, u32 features, diff --git a/net/netfilter/xt_SECMARK.c b/net/netfilter/xt_SECMARK.c index 4ad5fe27e08bc..097534dbc6226 100644 --- a/net/netfilter/xt_SECMARK.c +++ b/net/netfilter/xt_SECMARK.c @@ -30,10 +30,9 @@ MODULE_ALIAS("ip6t_SECMARK"); static u8 mode; static unsigned int -secmark_tg(struct sk_buff *skb, const struct xt_action_param *par) +secmark_tg(struct sk_buff *skb, const struct xt_secmark_target_info_v1 *info) { u32 secmark = 0; - const struct xt_secmark_target_info *info = par->targinfo; BUG_ON(info->mode != mode); @@ -49,7 +48,7 @@ secmark_tg(struct sk_buff *skb, const struct xt_action_param *par) return XT_CONTINUE; } -static int checkentry_lsm(struct xt_secmark_target_info *info) +static int checkentry_lsm(struct xt_secmark_target_info_v1 *info) { int err; @@ -81,15 +80,15 @@ static int checkentry_lsm(struct xt_secmark_target_info *info) return 0; } -static int secmark_tg_check(const struct xt_tgchk_param *par) +static int +secmark_tg_check(const char *table, struct xt_secmark_target_info_v1 *info) { - struct xt_secmark_target_info *info = par->targinfo; int err; - if (strcmp(par->table, "mangle") != 0 && - strcmp(par->table, "security") != 0) { + if (strcmp(table, "mangle") != 0 && + strcmp(table, "security") != 0) { pr_info_ratelimited("only valid in \'mangle\' or \'security\' table, not \'%s\'\n", - par->table); + table); return -EINVAL; } @@ -124,25 +123,76 @@ static void secmark_tg_destroy(const struct xt_tgdtor_param *par) } } -static struct xt_target secmark_tg_reg __read_mostly = { - .name = "SECMARK", - .revision = 0, - .family = NFPROTO_UNSPEC, - .checkentry = secmark_tg_check, - .destroy = secmark_tg_destroy, - .target = secmark_tg, - .targetsize = sizeof(struct xt_secmark_target_info), - .me = THIS_MODULE, +static int secmark_tg_check_v0(const struct xt_tgchk_param *par) +{ + struct xt_secmark_target_info *info = par->targinfo; + struct xt_secmark_target_info_v1 newinfo = { + .mode = info->mode, + }; + int ret; + + memcpy(newinfo.secctx, info->secctx, SECMARK_SECCTX_MAX); + + ret = secmark_tg_check(par->table, &newinfo); + info->secid = newinfo.secid; + + return ret; +} + +static unsigned int +secmark_tg_v0(struct sk_buff *skb, const struct xt_action_param *par) +{ + const struct xt_secmark_target_info *info = par->targinfo; + struct xt_secmark_target_info_v1 newinfo = { + .secid = info->secid, + }; + + return secmark_tg(skb, &newinfo); +} + +static int secmark_tg_check_v1(const struct xt_tgchk_param *par) +{ + return secmark_tg_check(par->table, par->targinfo); +} + +static unsigned int +secmark_tg_v1(struct sk_buff *skb, const struct xt_action_param *par) +{ + return secmark_tg(skb, par->targinfo); +} + +static struct xt_target secmark_tg_reg[] __read_mostly = { + { + .name = "SECMARK", + .revision = 0, + .family = NFPROTO_UNSPEC, + .checkentry = secmark_tg_check_v0, + .destroy = secmark_tg_destroy, + .target = secmark_tg_v0, + .targetsize = sizeof(struct xt_secmark_target_info), + .me = THIS_MODULE, + }, + { + .name = "SECMARK", + .revision = 1, + .family = NFPROTO_UNSPEC, + .checkentry = secmark_tg_check_v1, + .destroy = secmark_tg_destroy, + .target = secmark_tg_v1, + .targetsize = sizeof(struct xt_secmark_target_info_v1), + .usersize = offsetof(struct xt_secmark_target_info_v1, secid), + .me = THIS_MODULE, + }, }; static int __init secmark_tg_init(void) { - return xt_register_target(&secmark_tg_reg); + return xt_register_targets(secmark_tg_reg, ARRAY_SIZE(secmark_tg_reg)); } static void __exit secmark_tg_exit(void) { - xt_unregister_target(&secmark_tg_reg); + xt_unregister_targets(secmark_tg_reg, ARRAY_SIZE(secmark_tg_reg)); } module_init(secmark_tg_init); diff --git a/net/nfc/digital_dep.c b/net/nfc/digital_dep.c index 4f9a973988b2b..1eed0cf591908 100644 --- a/net/nfc/digital_dep.c +++ b/net/nfc/digital_dep.c @@ -1285,6 +1285,8 @@ static void digital_tg_recv_dep_req(struct nfc_digital_dev *ddev, void *arg, } rc = nfc_tm_data_received(ddev->nfc_dev, resp); + if (rc) + resp = NULL; exit: kfree_skb(ddev->chaining_skb); diff --git a/net/nfc/llcp_sock.c b/net/nfc/llcp_sock.c index bc269e83e1e55..59de4f54dd18c 100644 --- a/net/nfc/llcp_sock.c +++ b/net/nfc/llcp_sock.c @@ -121,12 +121,14 @@ static int llcp_sock_bind(struct socket *sock, struct sockaddr *addr, int alen) GFP_KERNEL); if (!llcp_sock->service_name) { nfc_llcp_local_put(llcp_sock->local); + llcp_sock->local = NULL; ret = -ENOMEM; goto put_dev; } llcp_sock->ssap = nfc_llcp_get_sdp_ssap(local, llcp_sock); if (llcp_sock->ssap == LLCP_SAP_MAX) { nfc_llcp_local_put(llcp_sock->local); + llcp_sock->local = NULL; kfree(llcp_sock->service_name); llcp_sock->service_name = NULL; ret = -EADDRINUSE; @@ -721,6 +723,7 @@ static int llcp_sock_connect(struct socket *sock, struct sockaddr *_addr, llcp_sock->ssap = nfc_llcp_get_local_ssap(local); if (llcp_sock->ssap == LLCP_SAP_MAX) { nfc_llcp_local_put(llcp_sock->local); + llcp_sock->local = NULL; ret = -ENOMEM; goto put_dev; } @@ -759,6 +762,7 @@ static int llcp_sock_connect(struct socket *sock, struct sockaddr *_addr, sock_unlink: nfc_llcp_put_ssap(local, llcp_sock->ssap); nfc_llcp_local_put(llcp_sock->local); + llcp_sock->local = NULL; nfc_llcp_sock_unlink(&local->connecting_sockets, sk); kfree(llcp_sock->service_name); diff --git a/net/openvswitch/actions.c b/net/openvswitch/actions.c index 8211e8e97c964..849fcf973c74b 100644 --- a/net/openvswitch/actions.c +++ b/net/openvswitch/actions.c @@ -892,17 +892,17 @@ static void ovs_fragment(struct net *net, struct vport *vport, } if (key->eth.type == htons(ETH_P_IP)) { - struct dst_entry ovs_dst; + struct rtable ovs_rt = { 0 }; unsigned long orig_dst; prepare_frag(vport, skb, orig_network_offset, ovs_key_mac_proto(key)); - dst_init(&ovs_dst, &ovs_dst_ops, NULL, 1, + dst_init(&ovs_rt.dst, &ovs_dst_ops, NULL, 1, DST_OBSOLETE_NONE, DST_NOCOUNT); - ovs_dst.dev = vport->dev; + ovs_rt.dst.dev = vport->dev; orig_dst = skb->_skb_refdst; - skb_dst_set_noref(skb, &ovs_dst); + skb_dst_set_noref(skb, &ovs_rt.dst); IPCB(skb)->frag_max_size = mru; ip_do_fragment(net, skb->sk, skb, ovs_vport_output); diff --git a/net/sctp/sm_make_chunk.c b/net/sctp/sm_make_chunk.c index ce6053be60bc8..dc51e14f568ee 100644 --- a/net/sctp/sm_make_chunk.c +++ b/net/sctp/sm_make_chunk.c @@ -3148,7 +3148,7 @@ static __be16 sctp_process_asconf_param(struct sctp_association *asoc, * primary. */ if (af->is_any(&addr)) - memcpy(&addr.v4, sctp_source(asconf), sizeof(addr)); + memcpy(&addr, sctp_source(asconf), sizeof(addr)); if (security_sctp_bind_connect(asoc->ep->base.sk, SCTP_PARAM_SET_PRIMARY, diff --git a/net/sctp/sm_statefuns.c b/net/sctp/sm_statefuns.c index a3033b74df54a..be5ea5e8b19e7 100644 --- a/net/sctp/sm_statefuns.c +++ b/net/sctp/sm_statefuns.c @@ -1856,20 +1856,35 @@ static enum sctp_disposition sctp_sf_do_dupcook_a( SCTP_TO(SCTP_EVENT_TIMEOUT_T4_RTO)); sctp_add_cmd_sf(commands, SCTP_CMD_PURGE_ASCONF_QUEUE, SCTP_NULL()); - repl = sctp_make_cookie_ack(new_asoc, chunk); + /* Update the content of current association. */ + if (sctp_assoc_update((struct sctp_association *)asoc, new_asoc)) { + struct sctp_chunk *abort; + + abort = sctp_make_abort(asoc, NULL, sizeof(struct sctp_errhdr)); + if (abort) { + sctp_init_cause(abort, SCTP_ERROR_RSRC_LOW, 0); + sctp_add_cmd_sf(commands, SCTP_CMD_REPLY, SCTP_CHUNK(abort)); + } + sctp_add_cmd_sf(commands, SCTP_CMD_SET_SK_ERR, SCTP_ERROR(ECONNABORTED)); + sctp_add_cmd_sf(commands, SCTP_CMD_ASSOC_FAILED, + SCTP_PERR(SCTP_ERROR_RSRC_LOW)); + SCTP_INC_STATS(net, SCTP_MIB_ABORTEDS); + SCTP_DEC_STATS(net, SCTP_MIB_CURRESTAB); + goto nomem; + } + + repl = sctp_make_cookie_ack(asoc, chunk); if (!repl) goto nomem; /* Report association restart to upper layer. */ ev = sctp_ulpevent_make_assoc_change(asoc, 0, SCTP_RESTART, 0, - new_asoc->c.sinit_num_ostreams, - new_asoc->c.sinit_max_instreams, + asoc->c.sinit_num_ostreams, + asoc->c.sinit_max_instreams, NULL, GFP_ATOMIC); if (!ev) goto nomem_ev; - /* Update the content of current association. */ - sctp_add_cmd_sf(commands, SCTP_CMD_UPDATE_ASSOC, SCTP_ASOC(new_asoc)); sctp_add_cmd_sf(commands, SCTP_CMD_EVENT_ULP, SCTP_ULPEVENT(ev)); if ((sctp_state(asoc, SHUTDOWN_PENDING) || sctp_state(asoc, SHUTDOWN_SENT)) && @@ -1933,7 +1948,8 @@ static enum sctp_disposition sctp_sf_do_dupcook_b( sctp_add_cmd_sf(commands, SCTP_CMD_UPDATE_ASSOC, SCTP_ASOC(new_asoc)); sctp_add_cmd_sf(commands, SCTP_CMD_NEW_STATE, SCTP_STATE(SCTP_STATE_ESTABLISHED)); - SCTP_INC_STATS(net, SCTP_MIB_CURRESTAB); + if (asoc->state < SCTP_STATE_ESTABLISHED) + SCTP_INC_STATS(net, SCTP_MIB_CURRESTAB); sctp_add_cmd_sf(commands, SCTP_CMD_HB_TIMERS_START, SCTP_NULL()); repl = sctp_make_cookie_ack(new_asoc, chunk); diff --git a/net/sctp/socket.c b/net/sctp/socket.c index 656bd15328836..1148f66917079 100644 --- a/net/sctp/socket.c +++ b/net/sctp/socket.c @@ -375,6 +375,18 @@ static struct sctp_af *sctp_sockaddr_af(struct sctp_sock *opt, return af; } +static void sctp_auto_asconf_init(struct sctp_sock *sp) +{ + struct net *net = sock_net(&sp->inet.sk); + + if (net->sctp.default_auto_asconf) { + spin_lock(&net->sctp.addr_wq_lock); + list_add_tail(&sp->auto_asconf_list, &net->sctp.auto_asconf_splist); + spin_unlock(&net->sctp.addr_wq_lock); + sp->do_auto_asconf = 1; + } +} + /* Bind a local address either to an endpoint or to an association. */ static int sctp_do_bind(struct sock *sk, union sctp_addr *addr, int len) { @@ -437,8 +449,10 @@ static int sctp_do_bind(struct sock *sk, union sctp_addr *addr, int len) } /* Refresh ephemeral port. */ - if (!bp->port) + if (!bp->port) { bp->port = inet_sk(sk)->inet_num; + sctp_auto_asconf_init(sp); + } /* Add the address to the bind address list. * Use GFP_ATOMIC since BHs will be disabled. @@ -1569,9 +1583,11 @@ static void sctp_close(struct sock *sk, long timeout) /* Supposedly, no process has access to the socket, but * the net layers still may. + * Also, sctp_destroy_sock() needs to be called with addr_wq_lock + * held and that should be grabbed before socket lock. */ - local_bh_disable(); - bh_lock_sock(sk); + spin_lock_bh(&net->sctp.addr_wq_lock); + bh_lock_sock_nested(sk); /* Hold the sock, since sk_common_release() will put sock_put() * and we have just a little more cleanup. @@ -1580,7 +1596,7 @@ static void sctp_close(struct sock *sk, long timeout) sk_common_release(sk); bh_unlock_sock(sk); - local_bh_enable(); + spin_unlock_bh(&net->sctp.addr_wq_lock); sock_put(sk); @@ -4774,16 +4790,6 @@ static int sctp_init_sock(struct sock *sk) sk_sockets_allocated_inc(sk); sock_prot_inuse_add(net, sk->sk_prot, 1); - if (net->sctp.default_auto_asconf) { - spin_lock(&sock_net(sk)->sctp.addr_wq_lock); - list_add_tail(&sp->auto_asconf_list, - &net->sctp.auto_asconf_splist); - sp->do_auto_asconf = 1; - spin_unlock(&sock_net(sk)->sctp.addr_wq_lock); - } else { - sp->do_auto_asconf = 0; - } - local_bh_enable(); return 0; @@ -4808,9 +4814,7 @@ static void sctp_destroy_sock(struct sock *sk) if (sp->do_auto_asconf) { sp->do_auto_asconf = 0; - spin_lock_bh(&sock_net(sk)->sctp.addr_wq_lock); list_del(&sp->auto_asconf_list); - spin_unlock_bh(&sock_net(sk)->sctp.addr_wq_lock); } sctp_endpoint_free(sp->ep); local_bh_disable(); @@ -8845,6 +8849,8 @@ static void sctp_sock_migrate(struct sock *oldsk, struct sock *newsk, sctp_bind_addr_dup(&newsp->ep->base.bind_addr, &oldsp->ep->base.bind_addr, GFP_KERNEL); + sctp_auto_asconf_init(newsp); + /* Move any messages in the old socket's receive queue that are for the * peeled off association to the new socket's receive queue. */ diff --git a/net/smc/af_smc.c b/net/smc/af_smc.c index 26dcd02b2d0ce..9aab4ab8161bd 100644 --- a/net/smc/af_smc.c +++ b/net/smc/af_smc.c @@ -1644,6 +1644,9 @@ static int smc_setsockopt(struct socket *sock, int level, int optname, struct smc_sock *smc; int val, rc; + if (level == SOL_TCP && optname == TCP_ULP) + return -EOPNOTSUPP; + smc = smc_sk(sk); /* generic setsockopts reaching us here always apply to the @@ -1665,7 +1668,6 @@ static int smc_setsockopt(struct socket *sock, int level, int optname, lock_sock(sk); switch (optname) { - case TCP_ULP: case TCP_FASTOPEN: case TCP_FASTOPEN_CONNECT: case TCP_FASTOPEN_KEY: diff --git a/net/tipc/netlink_compat.c b/net/tipc/netlink_compat.c index f8e111218a0ec..5086e27d3011e 100644 --- a/net/tipc/netlink_compat.c +++ b/net/tipc/netlink_compat.c @@ -671,7 +671,7 @@ static int tipc_nl_compat_link_dump(struct tipc_nl_compat_msg *msg, if (err) return err; - link_info.dest = nla_get_flag(link[TIPC_NLA_LINK_DEST]); + link_info.dest = htonl(nla_get_flag(link[TIPC_NLA_LINK_DEST])); link_info.up = htonl(nla_get_flag(link[TIPC_NLA_LINK_UP])); nla_strlcpy(link_info.str, link[TIPC_NLA_LINK_NAME], TIPC_MAX_LINK_NAME); diff --git a/net/vmw_vsock/vmci_transport.c b/net/vmw_vsock/vmci_transport.c index c3d5ab01fba7b..42ab3e2ac0602 100644 --- a/net/vmw_vsock/vmci_transport.c +++ b/net/vmw_vsock/vmci_transport.c @@ -584,8 +584,7 @@ vmci_transport_queue_pair_alloc(struct vmci_qp **qpair, peer, flags, VMCI_NO_PRIVILEGE_FLAGS); out: if (err < 0) { - pr_err("Could not attach to queue pair with %d\n", - err); + pr_err_once("Could not attach to queue pair with %d\n", err); err = vmci_transport_error_to_vsock_error(err); } diff --git a/net/wireless/scan.c b/net/wireless/scan.c index e5d61ba837add..67b2747ad9ef8 100644 --- a/net/wireless/scan.c +++ b/net/wireless/scan.c @@ -1036,6 +1036,8 @@ cfg80211_bss_update(struct cfg80211_registered_device *rdev, if (rdev->bss_entries >= bss_entries_limit && !cfg80211_bss_expire_oldest(rdev)) { + if (!list_empty(&new->hidden_list)) + list_del(&new->hidden_list); kfree(new); goto drop; } diff --git a/net/xdp/xsk_queue.h b/net/xdp/xsk_queue.h index fe96c0d039f2f..cf7cbb5dd9180 100644 --- a/net/xdp/xsk_queue.h +++ b/net/xdp/xsk_queue.h @@ -245,12 +245,15 @@ static inline void xskq_produce_flush_desc(struct xsk_queue *q) static inline bool xskq_full_desc(struct xsk_queue *q) { - return xskq_nb_avail(q, q->nentries) == q->nentries; + /* No barriers needed since data is not accessed */ + return READ_ONCE(q->ring->producer) - READ_ONCE(q->ring->consumer) == + q->nentries; } static inline bool xskq_empty_desc(struct xsk_queue *q) { - return xskq_nb_free(q, q->prod_tail, q->nentries) == q->nentries; + /* No barriers needed since data is not accessed */ + return READ_ONCE(q->ring->consumer) == READ_ONCE(q->ring->producer); } void xskq_set_umem(struct xsk_queue *q, struct xdp_umem_props *umem_props); diff --git a/samples/bpf/tracex1_kern.c b/samples/bpf/tracex1_kern.c index 107da148820fc..9c74b45c5720f 100644 --- a/samples/bpf/tracex1_kern.c +++ b/samples/bpf/tracex1_kern.c @@ -20,7 +20,7 @@ SEC("kprobe/__netif_receive_skb_core") int bpf_prog1(struct pt_regs *ctx) { - /* attaches to kprobe netif_receive_skb, + /* attaches to kprobe __netif_receive_skb_core, * looks for packets on loobpack device and prints them */ char devname[IFNAMSIZ]; @@ -29,7 +29,7 @@ int bpf_prog1(struct pt_regs *ctx) int len; /* non-portable! works for the given kernel only */ - skb = (struct sk_buff *) PT_REGS_PARM1(ctx); + bpf_probe_read_kernel(&skb, sizeof(skb), (void *)PT_REGS_PARM1(ctx)); dev = _(skb->dev); len = _(skb->len); diff --git a/samples/kfifo/bytestream-example.c b/samples/kfifo/bytestream-example.c index 2fca916d9edfd..a7f5ee8b6edcf 100644 --- a/samples/kfifo/bytestream-example.c +++ b/samples/kfifo/bytestream-example.c @@ -124,8 +124,10 @@ static ssize_t fifo_write(struct file *file, const char __user *buf, ret = kfifo_from_user(&test, buf, count, &copied); mutex_unlock(&write_lock); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static ssize_t fifo_read(struct file *file, char __user *buf, @@ -140,8 +142,10 @@ static ssize_t fifo_read(struct file *file, char __user *buf, ret = kfifo_to_user(&test, buf, count, &copied); mutex_unlock(&read_lock); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static const struct file_operations fifo_fops = { diff --git a/samples/kfifo/inttype-example.c b/samples/kfifo/inttype-example.c index 8dc3c2e7105a0..a326a37e91631 100644 --- a/samples/kfifo/inttype-example.c +++ b/samples/kfifo/inttype-example.c @@ -117,8 +117,10 @@ static ssize_t fifo_write(struct file *file, const char __user *buf, ret = kfifo_from_user(&test, buf, count, &copied); mutex_unlock(&write_lock); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static ssize_t fifo_read(struct file *file, char __user *buf, @@ -133,8 +135,10 @@ static ssize_t fifo_read(struct file *file, char __user *buf, ret = kfifo_to_user(&test, buf, count, &copied); mutex_unlock(&read_lock); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static const struct file_operations fifo_fops = { diff --git a/samples/kfifo/record-example.c b/samples/kfifo/record-example.c index 2d7529eeb2940..deb87a2e4e6bc 100644 --- a/samples/kfifo/record-example.c +++ b/samples/kfifo/record-example.c @@ -131,8 +131,10 @@ static ssize_t fifo_write(struct file *file, const char __user *buf, ret = kfifo_from_user(&test, buf, count, &copied); mutex_unlock(&write_lock); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static ssize_t fifo_read(struct file *file, char __user *buf, @@ -147,8 +149,10 @@ static ssize_t fifo_read(struct file *file, char __user *buf, ret = kfifo_to_user(&test, buf, count, &copied); mutex_unlock(&read_lock); + if (ret) + return ret; - return ret ? ret : copied; + return copied; } static const struct file_operations fifo_fops = { diff --git a/scripts/bloat-o-meter b/scripts/bloat-o-meter index a923f05edb366..e12daed3f41d7 100755 --- a/scripts/bloat-o-meter +++ b/scripts/bloat-o-meter @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/env python3 # # Copyright 2004 Matt Mackall # diff --git a/scripts/config b/scripts/config index eee5b7f3a092a..8c8d7c3d7accc 100755 --- a/scripts/config +++ b/scripts/config @@ -1,4 +1,4 @@ -#!/bin/bash +#!/usr/bin/env bash # SPDX-License-Identifier: GPL-2.0 # Manipulate options in a .config file from the command line diff --git a/scripts/diffconfig b/scripts/diffconfig index 89abf777f1973..d5da5fa05d1d3 100755 --- a/scripts/diffconfig +++ b/scripts/diffconfig @@ -1,4 +1,4 @@ -#!/usr/bin/python +#!/usr/bin/env python3 # SPDX-License-Identifier: GPL-2.0 # # diffconfig - a tool to compare .config files. diff --git a/scripts/kconfig/nconf.c b/scripts/kconfig/nconf.c index c8ff1c99dd5c7..552cf7557c7a9 100644 --- a/scripts/kconfig/nconf.c +++ b/scripts/kconfig/nconf.c @@ -504,8 +504,8 @@ static int get_mext_match(const char *match_str, match_f flag) else if (flag == FIND_NEXT_MATCH_UP) --match_start; + match_start = (match_start + items_num) % items_num; index = match_start; - index = (index + items_num) % items_num; while (true) { char *str = k_menu_items[index].str; if (strcasestr(str, match_str) != NULL) diff --git a/scripts/recordmcount.pl b/scripts/recordmcount.pl index 9a8fe8ea6b037..657e69125a462 100755 --- a/scripts/recordmcount.pl +++ b/scripts/recordmcount.pl @@ -395,7 +395,7 @@ if ($arch eq "x86_64") { $mcount_regex = "^\\s*([0-9a-fA-F]+):.*\\s_mcount\$"; } elsif ($arch eq "riscv") { $function_regex = "^([0-9a-fA-F]+)\\s+<([^.0-9][0-9a-zA-Z_\\.]+)>:"; - $mcount_regex = "^\\s*([0-9a-fA-F]+):\\sR_RISCV_CALL\\s_mcount\$"; + $mcount_regex = "^\\s*([0-9a-fA-F]+):\\sR_RISCV_CALL(_PLT)?\\s_?mcount\$"; $type = ".quad"; $alignment = 2; } elsif ($arch eq "nds32") { diff --git a/scripts/split-man.pl b/scripts/split-man.pl index c3db607ee9ec1..96bd99dc977a5 100755 --- a/scripts/split-man.pl +++ b/scripts/split-man.pl @@ -1,4 +1,4 @@ -#!/usr/bin/perl +#!/usr/bin/env perl # SPDX-License-Identifier: GPL-2.0 # # Author: Mauro Carvalho Chehab diff --git a/security/commoncap.c b/security/commoncap.c index a1dee0ab345a2..876cfe01d9391 100644 --- a/security/commoncap.c +++ b/security/commoncap.c @@ -397,7 +397,7 @@ int cap_inode_getsecurity(struct inode *inode, const char *name, void **buffer, &tmpbuf, size, GFP_NOFS); dput(dentry); - if (ret < 0) + if (ret < 0 || !tmpbuf) return ret; fs_ns = inode->i_sb->s_user_ns; diff --git a/sound/core/init.c b/sound/core/init.c index 16b7cc7aa66b5..3eafa15006f8a 100644 --- a/sound/core/init.c +++ b/sound/core/init.c @@ -405,10 +405,8 @@ int snd_card_disconnect(struct snd_card *card) return 0; } card->shutdown = 1; - spin_unlock(&card->files_lock); /* replace file->f_op with special dummy operations */ - spin_lock(&card->files_lock); list_for_each_entry(mfile, &card->files_list, list) { /* it's critical part, use endless loop */ /* we have no room to fail */ diff --git a/sound/isa/sb/emu8000.c b/sound/isa/sb/emu8000.c index d56973b770c7d..24b91cb328399 100644 --- a/sound/isa/sb/emu8000.c +++ b/sound/isa/sb/emu8000.c @@ -1042,8 +1042,10 @@ snd_emu8000_create_mixer(struct snd_card *card, struct snd_emu8000 *emu) memset(emu->controls, 0, sizeof(emu->controls)); for (i = 0; i < EMU8000_NUM_CONTROLS; i++) { - if ((err = snd_ctl_add(card, emu->controls[i] = snd_ctl_new1(mixer_defs[i], emu))) < 0) + if ((err = snd_ctl_add(card, emu->controls[i] = snd_ctl_new1(mixer_defs[i], emu))) < 0) { + emu->controls[i] = NULL; goto __error; + } } return 0; diff --git a/sound/isa/sb/sb16_csp.c b/sound/isa/sb/sb16_csp.c index bf3db0d2ea12b..2e00b64ef13bf 100644 --- a/sound/isa/sb/sb16_csp.c +++ b/sound/isa/sb/sb16_csp.c @@ -1059,10 +1059,14 @@ static int snd_sb_qsound_build(struct snd_sb_csp * p) spin_lock_init(&p->q_lock); - if ((err = snd_ctl_add(card, p->qsound_switch = snd_ctl_new1(&snd_sb_qsound_switch, p))) < 0) + if ((err = snd_ctl_add(card, p->qsound_switch = snd_ctl_new1(&snd_sb_qsound_switch, p))) < 0) { + p->qsound_switch = NULL; goto __error; - if ((err = snd_ctl_add(card, p->qsound_space = snd_ctl_new1(&snd_sb_qsound_space, p))) < 0) + } + if ((err = snd_ctl_add(card, p->qsound_space = snd_ctl_new1(&snd_sb_qsound_space, p))) < 0) { + p->qsound_space = NULL; goto __error; + } return 0; diff --git a/sound/pci/hda/hda_generic.c b/sound/pci/hda/hda_generic.c index b9f7b23ae3789..6099a9f1cb3d6 100644 --- a/sound/pci/hda/hda_generic.c +++ b/sound/pci/hda/hda_generic.c @@ -1214,11 +1214,17 @@ static const char *get_line_out_pfx(struct hda_codec *codec, int ch, *index = ch; return "Headphone"; case AUTO_PIN_LINE_OUT: - /* This deals with the case where we have two DACs and - * one LO, one HP and one Speaker */ - if (!ch && cfg->speaker_outs && cfg->hp_outs) { - bool hp_lo_shared = !path_has_mixer(codec, spec->hp_paths[0], ctl_type); - bool spk_lo_shared = !path_has_mixer(codec, spec->speaker_paths[0], ctl_type); + /* This deals with the case where one HP or one Speaker or + * one HP + one Speaker need to share the DAC with LO + */ + if (!ch) { + bool hp_lo_shared = false, spk_lo_shared = false; + + if (cfg->speaker_outs) + spk_lo_shared = !path_has_mixer(codec, + spec->speaker_paths[0], ctl_type); + if (cfg->hp_outs) + hp_lo_shared = !path_has_mixer(codec, spec->hp_paths[0], ctl_type); if (hp_lo_shared && spk_lo_shared) return spec->vmaster_mute.hook ? "PCM" : "Master"; if (hp_lo_shared) diff --git a/sound/pci/hda/patch_conexant.c b/sound/pci/hda/patch_conexant.c index 7d471ecc1ca03..8851cd11dc9ca 100644 --- a/sound/pci/hda/patch_conexant.c +++ b/sound/pci/hda/patch_conexant.c @@ -911,18 +911,18 @@ static const struct snd_pci_quirk cxt5066_fixups[] = { SND_PCI_QUIRK(0x103c, 0x8079, "HP EliteBook 840 G3", CXT_FIXUP_HP_DOCK), SND_PCI_QUIRK(0x103c, 0x807C, "HP EliteBook 820 G3", CXT_FIXUP_HP_DOCK), SND_PCI_QUIRK(0x103c, 0x80FD, "HP ProBook 640 G2", CXT_FIXUP_HP_DOCK), - SND_PCI_QUIRK(0x103c, 0x828c, "HP EliteBook 840 G4", CXT_FIXUP_HP_DOCK), - SND_PCI_QUIRK(0x103c, 0x83b2, "HP EliteBook 840 G5", CXT_FIXUP_HP_DOCK), - SND_PCI_QUIRK(0x103c, 0x83b3, "HP EliteBook 830 G5", CXT_FIXUP_HP_DOCK), - SND_PCI_QUIRK(0x103c, 0x83d3, "HP ProBook 640 G4", CXT_FIXUP_HP_DOCK), - SND_PCI_QUIRK(0x103c, 0x8174, "HP Spectre x360", CXT_FIXUP_HP_SPECTRE), SND_PCI_QUIRK(0x103c, 0x8115, "HP Z1 Gen3", CXT_FIXUP_HP_GATE_MIC), SND_PCI_QUIRK(0x103c, 0x814f, "HP ZBook 15u G3", CXT_FIXUP_MUTE_LED_GPIO), + SND_PCI_QUIRK(0x103c, 0x8174, "HP Spectre x360", CXT_FIXUP_HP_SPECTRE), SND_PCI_QUIRK(0x103c, 0x822e, "HP ProBook 440 G4", CXT_FIXUP_MUTE_LED_GPIO), - SND_PCI_QUIRK(0x103c, 0x836e, "HP ProBook 455 G5", CXT_FIXUP_MUTE_LED_GPIO), - SND_PCI_QUIRK(0x103c, 0x837f, "HP ProBook 470 G5", CXT_FIXUP_MUTE_LED_GPIO), + SND_PCI_QUIRK(0x103c, 0x828c, "HP EliteBook 840 G4", CXT_FIXUP_HP_DOCK), SND_PCI_QUIRK(0x103c, 0x8299, "HP 800 G3 SFF", CXT_FIXUP_HP_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x103c, 0x829a, "HP 800 G3 DM", CXT_FIXUP_HP_MIC_NO_PRESENCE), + SND_PCI_QUIRK(0x103c, 0x836e, "HP ProBook 455 G5", CXT_FIXUP_MUTE_LED_GPIO), + SND_PCI_QUIRK(0x103c, 0x837f, "HP ProBook 470 G5", CXT_FIXUP_MUTE_LED_GPIO), + SND_PCI_QUIRK(0x103c, 0x83b2, "HP EliteBook 840 G5", CXT_FIXUP_HP_DOCK), + SND_PCI_QUIRK(0x103c, 0x83b3, "HP EliteBook 830 G5", CXT_FIXUP_HP_DOCK), + SND_PCI_QUIRK(0x103c, 0x83d3, "HP ProBook 640 G4", CXT_FIXUP_HP_DOCK), SND_PCI_QUIRK(0x103c, 0x8402, "HP ProBook 645 G4", CXT_FIXUP_MUTE_LED_GPIO), SND_PCI_QUIRK(0x103c, 0x8455, "HP Z2 G4", CXT_FIXUP_HP_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x103c, 0x8456, "HP Z2 G4 SFF", CXT_FIXUP_HP_MIC_NO_PRESENCE), diff --git a/sound/pci/hda/patch_realtek.c b/sound/pci/hda/patch_realtek.c index f456e5f67824c..c4a9141a449cc 100644 --- a/sound/pci/hda/patch_realtek.c +++ b/sound/pci/hda/patch_realtek.c @@ -2445,13 +2445,13 @@ static const struct snd_pci_quirk alc882_fixup_tbl[] = { ALC882_FIXUP_ACER_ASPIRE_8930G), SND_PCI_QUIRK(0x1025, 0x0146, "Acer Aspire 6935G", ALC882_FIXUP_ACER_ASPIRE_8930G), + SND_PCI_QUIRK(0x1025, 0x0142, "Acer Aspire 7730G", + ALC882_FIXUP_ACER_ASPIRE_4930G), + SND_PCI_QUIRK(0x1025, 0x0155, "Packard-Bell M5120", ALC882_FIXUP_PB_M5210), SND_PCI_QUIRK(0x1025, 0x015e, "Acer Aspire 6930G", ALC882_FIXUP_ACER_ASPIRE_4930G), SND_PCI_QUIRK(0x1025, 0x0166, "Acer Aspire 6530G", ALC882_FIXUP_ACER_ASPIRE_4930G), - SND_PCI_QUIRK(0x1025, 0x0142, "Acer Aspire 7730G", - ALC882_FIXUP_ACER_ASPIRE_4930G), - SND_PCI_QUIRK(0x1025, 0x0155, "Packard-Bell M5120", ALC882_FIXUP_PB_M5210), SND_PCI_QUIRK(0x1025, 0x021e, "Acer Aspire 5739G", ALC882_FIXUP_ACER_ASPIRE_4930G), SND_PCI_QUIRK(0x1025, 0x0259, "Acer Aspire 5935", ALC889_FIXUP_DAC_ROUTE), @@ -2464,11 +2464,11 @@ static const struct snd_pci_quirk alc882_fixup_tbl[] = { SND_PCI_QUIRK(0x1043, 0x835f, "Asus Eee 1601", ALC888_FIXUP_EEE1601), SND_PCI_QUIRK(0x1043, 0x84bc, "ASUS ET2700", ALC887_FIXUP_ASUS_BASS), SND_PCI_QUIRK(0x1043, 0x8691, "ASUS ROG Ranger VIII", ALC882_FIXUP_GPIO3), + SND_PCI_QUIRK(0x104d, 0x9043, "Sony Vaio VGC-LN51JGB", ALC882_FIXUP_NO_PRIMARY_HP), + SND_PCI_QUIRK(0x104d, 0x9044, "Sony VAIO AiO", ALC882_FIXUP_NO_PRIMARY_HP), SND_PCI_QUIRK(0x104d, 0x9047, "Sony Vaio TT", ALC889_FIXUP_VAIO_TT), SND_PCI_QUIRK(0x104d, 0x905a, "Sony Vaio Z", ALC882_FIXUP_NO_PRIMARY_HP), SND_PCI_QUIRK(0x104d, 0x9060, "Sony Vaio VPCL14M1R", ALC882_FIXUP_NO_PRIMARY_HP), - SND_PCI_QUIRK(0x104d, 0x9043, "Sony Vaio VGC-LN51JGB", ALC882_FIXUP_NO_PRIMARY_HP), - SND_PCI_QUIRK(0x104d, 0x9044, "Sony VAIO AiO", ALC882_FIXUP_NO_PRIMARY_HP), /* All Apple entries are in codec SSIDs */ SND_PCI_QUIRK(0x106b, 0x00a0, "MacBookPro 3,1", ALC889_FIXUP_MBP_VREF), @@ -2511,9 +2511,19 @@ static const struct snd_pci_quirk alc882_fixup_tbl[] = { SND_PCI_QUIRK(0x1462, 0xda57, "MSI Z270-Gaming", ALC1220_FIXUP_GB_DUAL_CODECS), SND_PCI_QUIRK_VENDOR(0x1462, "MSI", ALC882_FIXUP_GPIO3), SND_PCI_QUIRK(0x147b, 0x107a, "Abit AW9D-MAX", ALC882_FIXUP_ABIT_AW9D_MAX), + SND_PCI_QUIRK(0x1558, 0x50d3, "Clevo PC50[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x65d1, "Clevo PB51[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x65d2, "Clevo PB51R[CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x65e1, "Clevo PB51[ED][DF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x65e5, "Clevo PC50D[PRS](?:-D|-G)?", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x67d1, "Clevo PB71[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x67e1, "Clevo PB71[DE][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x67e5, "Clevo PC70D[PRS](?:-D|-G)?", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x70d1, "Clevo PC70[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), + SND_PCI_QUIRK(0x1558, 0x7714, "Clevo X170", ALC1220_FIXUP_CLEVO_PB51ED_PINS), SND_PCI_QUIRK(0x1558, 0x9501, "Clevo P950HR", ALC1220_FIXUP_CLEVO_P950), SND_PCI_QUIRK(0x1558, 0x9506, "Clevo P955HQ", ALC1220_FIXUP_CLEVO_P950), - SND_PCI_QUIRK(0x1558, 0x950A, "Clevo P955H[PR]", ALC1220_FIXUP_CLEVO_P950), + SND_PCI_QUIRK(0x1558, 0x950a, "Clevo P955H[PR]", ALC1220_FIXUP_CLEVO_P950), SND_PCI_QUIRK(0x1558, 0x95e1, "Clevo P95xER", ALC1220_FIXUP_CLEVO_P950), SND_PCI_QUIRK(0x1558, 0x95e2, "Clevo P950ER", ALC1220_FIXUP_CLEVO_P950), SND_PCI_QUIRK(0x1558, 0x95e3, "Clevo P955[ER]T", ALC1220_FIXUP_CLEVO_P950), @@ -2523,14 +2533,6 @@ static const struct snd_pci_quirk alc882_fixup_tbl[] = { SND_PCI_QUIRK(0x1558, 0x96e1, "Clevo P960[ER][CDFN]-K", ALC1220_FIXUP_CLEVO_P950), SND_PCI_QUIRK(0x1558, 0x97e1, "Clevo P970[ER][CDFN]", ALC1220_FIXUP_CLEVO_P950), SND_PCI_QUIRK(0x1558, 0x97e2, "Clevo P970RC-M", ALC1220_FIXUP_CLEVO_P950), - SND_PCI_QUIRK(0x1558, 0x50d3, "Clevo PC50[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x65d1, "Clevo PB51[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x65d2, "Clevo PB51R[CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x65e1, "Clevo PB51[ED][DF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x67d1, "Clevo PB71[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x67e1, "Clevo PB71[DE][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x70d1, "Clevo PC70[ER][CDF]", ALC1220_FIXUP_CLEVO_PB51ED_PINS), - SND_PCI_QUIRK(0x1558, 0x7714, "Clevo X170", ALC1220_FIXUP_CLEVO_PB51ED_PINS), SND_PCI_QUIRK_VENDOR(0x1558, "Clevo laptop", ALC882_FIXUP_EAPD), SND_PCI_QUIRK(0x161f, 0x2054, "Medion laptop", ALC883_FIXUP_EAPD), SND_PCI_QUIRK(0x17aa, 0x3a0d, "Lenovo Y530", ALC882_FIXUP_LENOVO_Y530), @@ -7007,8 +7009,8 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x1028, 0x0738, "Dell Precision 5820", ALC269_FIXUP_NO_SHUTUP), SND_PCI_QUIRK(0x1028, 0x075c, "Dell XPS 27 7760", ALC298_FIXUP_SPK_VOLUME), SND_PCI_QUIRK(0x1028, 0x075d, "Dell AIO", ALC298_FIXUP_SPK_VOLUME), - SND_PCI_QUIRK(0x1028, 0x07b0, "Dell Precision 7520", ALC295_FIXUP_DISABLE_DAC3), SND_PCI_QUIRK(0x1028, 0x0798, "Dell Inspiron 17 7000 Gaming", ALC256_FIXUP_DELL_INSPIRON_7559_SUBWOOFER), + SND_PCI_QUIRK(0x1028, 0x07b0, "Dell Precision 7520", ALC295_FIXUP_DISABLE_DAC3), SND_PCI_QUIRK(0x1028, 0x080c, "Dell WYSE", ALC225_FIXUP_DELL_WYSE_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x1028, 0x084b, "Dell", ALC274_FIXUP_DELL_AIO_LINEOUT_VERB), SND_PCI_QUIRK(0x1028, 0x084e, "Dell", ALC274_FIXUP_DELL_AIO_LINEOUT_VERB), @@ -7018,8 +7020,8 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x1028, 0x08ad, "Dell WYSE AIO", ALC225_FIXUP_DELL_WYSE_AIO_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x1028, 0x08ae, "Dell WYSE NB", ALC225_FIXUP_DELL1_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x1028, 0x0935, "Dell", ALC274_FIXUP_DELL_AIO_LINEOUT_VERB), - SND_PCI_QUIRK(0x1028, 0x097e, "Dell Precision", ALC289_FIXUP_DUAL_SPK), SND_PCI_QUIRK(0x1028, 0x097d, "Dell Precision", ALC289_FIXUP_DUAL_SPK), + SND_PCI_QUIRK(0x1028, 0x097e, "Dell Precision", ALC289_FIXUP_DUAL_SPK), SND_PCI_QUIRK(0x1028, 0x098d, "Dell Precision", ALC233_FIXUP_ASUS_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x1028, 0x09bf, "Dell Precision", ALC233_FIXUP_ASUS_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x1028, 0x164a, "Dell", ALC293_FIXUP_DELL1_MIC_NO_PRESENCE), @@ -7027,35 +7029,18 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x103c, 0x1586, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC2), SND_PCI_QUIRK(0x103c, 0x18e6, "HP", ALC269_FIXUP_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x218b, "HP", ALC269_FIXUP_LIMIT_INT_MIC_BOOST_MUTE_LED), - SND_PCI_QUIRK(0x103c, 0x225f, "HP", ALC280_FIXUP_HP_GPIO2_MIC_HOTKEY), - /* ALC282 */ SND_PCI_QUIRK(0x103c, 0x21f9, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2210, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2214, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x221b, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), + SND_PCI_QUIRK(0x103c, 0x221c, "HP EliteBook 755 G2", ALC280_FIXUP_HP_HEADSET_MIC), + SND_PCI_QUIRK(0x103c, 0x2221, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), + SND_PCI_QUIRK(0x103c, 0x2225, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2236, "HP", ALC269_FIXUP_HP_LINE1_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2237, "HP", ALC269_FIXUP_HP_LINE1_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2238, "HP", ALC269_FIXUP_HP_LINE1_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2239, "HP", ALC269_FIXUP_HP_LINE1_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x224b, "HP", ALC269_FIXUP_HP_LINE1_MIC1_LED), - SND_PCI_QUIRK(0x103c, 0x2268, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x226a, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x226b, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x226e, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x2271, "HP", ALC286_FIXUP_HP_GPIO_LED), - SND_PCI_QUIRK(0x103c, 0x2272, "HP", ALC280_FIXUP_HP_DOCK_PINS), - SND_PCI_QUIRK(0x103c, 0x2273, "HP", ALC280_FIXUP_HP_DOCK_PINS), - SND_PCI_QUIRK(0x103c, 0x229e, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x22b2, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x22b7, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x22bf, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x22cf, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x22db, "HP", ALC280_FIXUP_HP_9480M), - SND_PCI_QUIRK(0x103c, 0x22dc, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), - SND_PCI_QUIRK(0x103c, 0x22fb, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), - /* ALC290 */ - SND_PCI_QUIRK(0x103c, 0x221b, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), - SND_PCI_QUIRK(0x103c, 0x2221, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), - SND_PCI_QUIRK(0x103c, 0x2225, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2253, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2254, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2255, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), @@ -7063,26 +7048,41 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x103c, 0x2257, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2259, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x225a, "HP", ALC269_FIXUP_HP_DOCK_GPIO_MIC1_LED), + SND_PCI_QUIRK(0x103c, 0x225f, "HP", ALC280_FIXUP_HP_GPIO2_MIC_HOTKEY), SND_PCI_QUIRK(0x103c, 0x2260, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2263, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2264, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2265, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x2268, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x226a, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x226b, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x226e, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x2271, "HP", ALC286_FIXUP_HP_GPIO_LED), SND_PCI_QUIRK(0x103c, 0x2272, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), + SND_PCI_QUIRK(0x103c, 0x2272, "HP", ALC280_FIXUP_HP_DOCK_PINS), SND_PCI_QUIRK(0x103c, 0x2273, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), + SND_PCI_QUIRK(0x103c, 0x2273, "HP", ALC280_FIXUP_HP_DOCK_PINS), SND_PCI_QUIRK(0x103c, 0x2278, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x227f, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2282, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x228b, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x228e, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x229e, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x22b2, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x22b7, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x22bf, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x22c4, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x22c5, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x22c7, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x22c8, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x22c4, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x22cf, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), + SND_PCI_QUIRK(0x103c, 0x22db, "HP", ALC280_FIXUP_HP_9480M), + SND_PCI_QUIRK(0x103c, 0x22dc, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), + SND_PCI_QUIRK(0x103c, 0x22fb, "HP", ALC269_FIXUP_HP_GPIO_MIC1_LED), SND_PCI_QUIRK(0x103c, 0x2334, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2335, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2336, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), SND_PCI_QUIRK(0x103c, 0x2337, "HP", ALC269_FIXUP_HP_MUTE_LED_MIC1), - SND_PCI_QUIRK(0x103c, 0x221c, "HP EliteBook 755 G2", ALC280_FIXUP_HP_HEADSET_MIC), SND_PCI_QUIRK(0x103c, 0x802e, "HP Z240 SFF", ALC221_FIXUP_HP_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x103c, 0x802f, "HP Z240", ALC221_FIXUP_HP_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x103c, 0x820d, "HP Pavilion 15", ALC269_FIXUP_HP_MUTE_LED_MIC3), @@ -7128,12 +7128,12 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x1043, 0x8398, "ASUS P1005", ALC269_FIXUP_STEREO_DMIC), SND_PCI_QUIRK(0x1043, 0x83ce, "ASUS P1005", ALC269_FIXUP_STEREO_DMIC), SND_PCI_QUIRK(0x1043, 0x8516, "ASUS X101CH", ALC269_FIXUP_ASUS_X101), - SND_PCI_QUIRK(0x104d, 0x90b5, "Sony VAIO Pro 11", ALC286_FIXUP_SONY_MIC_NO_PRESENCE), - SND_PCI_QUIRK(0x104d, 0x90b6, "Sony VAIO Pro 13", ALC286_FIXUP_SONY_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x104d, 0x9073, "Sony VAIO", ALC275_FIXUP_SONY_VAIO_GPIO2), SND_PCI_QUIRK(0x104d, 0x907b, "Sony VAIO", ALC275_FIXUP_SONY_HWEQ), SND_PCI_QUIRK(0x104d, 0x9084, "Sony VAIO", ALC275_FIXUP_SONY_HWEQ), SND_PCI_QUIRK(0x104d, 0x9099, "Sony VAIO S13", ALC275_FIXUP_SONY_DISABLE_AAMIX), + SND_PCI_QUIRK(0x104d, 0x90b5, "Sony VAIO Pro 11", ALC286_FIXUP_SONY_MIC_NO_PRESENCE), + SND_PCI_QUIRK(0x104d, 0x90b6, "Sony VAIO Pro 13", ALC286_FIXUP_SONY_MIC_NO_PRESENCE), SND_PCI_QUIRK(0x10cf, 0x1475, "Lifebook", ALC269_FIXUP_LIFEBOOK), SND_PCI_QUIRK(0x10cf, 0x159f, "Lifebook E780", ALC269_FIXUP_LIFEBOOK_NO_HP_TO_LINEOUT), SND_PCI_QUIRK(0x10cf, 0x15dc, "Lifebook T731", ALC269_FIXUP_LIFEBOOK_HP_PIN), @@ -7199,9 +7199,9 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x17aa, 0x21b8, "Thinkpad Edge 14", ALC269_FIXUP_SKU_IGNORE), SND_PCI_QUIRK(0x17aa, 0x21ca, "Thinkpad L412", ALC269_FIXUP_SKU_IGNORE), SND_PCI_QUIRK(0x17aa, 0x21e9, "Thinkpad Edge 15", ALC269_FIXUP_SKU_IGNORE), + SND_PCI_QUIRK(0x17aa, 0x21f3, "Thinkpad T430", ALC269_FIXUP_LENOVO_DOCK), SND_PCI_QUIRK(0x17aa, 0x21f6, "Thinkpad T530", ALC269_FIXUP_LENOVO_DOCK_LIMIT_BOOST), SND_PCI_QUIRK(0x17aa, 0x21fa, "Thinkpad X230", ALC269_FIXUP_LENOVO_DOCK), - SND_PCI_QUIRK(0x17aa, 0x21f3, "Thinkpad T430", ALC269_FIXUP_LENOVO_DOCK), SND_PCI_QUIRK(0x17aa, 0x21fb, "Thinkpad T430s", ALC269_FIXUP_LENOVO_DOCK), SND_PCI_QUIRK(0x17aa, 0x2203, "Thinkpad X230 Tablet", ALC269_FIXUP_LENOVO_DOCK), SND_PCI_QUIRK(0x17aa, 0x2208, "Thinkpad T431s", ALC269_FIXUP_LENOVO_DOCK), @@ -7243,6 +7243,7 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x17aa, 0x3902, "Lenovo E50-80", ALC269_FIXUP_DMIC_THINKPAD_ACPI), SND_PCI_QUIRK(0x17aa, 0x3977, "IdeaPad S210", ALC283_FIXUP_INT_MIC), SND_PCI_QUIRK(0x17aa, 0x3978, "Lenovo B50-70", ALC269_FIXUP_DMIC_THINKPAD_ACPI), + SND_PCI_QUIRK(0x17aa, 0x3bf8, "Quanta FL1", ALC269_FIXUP_PCM_44K), SND_PCI_QUIRK(0x17aa, 0x5013, "Thinkpad", ALC269_FIXUP_LIMIT_INT_MIC_BOOST), SND_PCI_QUIRK(0x17aa, 0x501a, "Thinkpad", ALC283_FIXUP_INT_MIC), SND_PCI_QUIRK(0x17aa, 0x501e, "Thinkpad L440", ALC292_FIXUP_TPT440_DOCK), @@ -7261,7 +7262,6 @@ static const struct snd_pci_quirk alc269_fixup_tbl[] = { SND_PCI_QUIRK(0x17aa, 0x5109, "Thinkpad", ALC269_FIXUP_LIMIT_INT_MIC_BOOST), SND_PCI_QUIRK(0x17aa, 0x511e, "Thinkpad", ALC298_FIXUP_TPT470_DOCK), SND_PCI_QUIRK(0x17aa, 0x511f, "Thinkpad", ALC298_FIXUP_TPT470_DOCK), - SND_PCI_QUIRK(0x17aa, 0x3bf8, "Quanta FL1", ALC269_FIXUP_PCM_44K), SND_PCI_QUIRK(0x17aa, 0x9e54, "LENOVO NB", ALC269_FIXUP_LENOVO_EAPD), SND_PCI_QUIRK(0x19e5, 0x3204, "Huawei MBXP", ALC256_FIXUP_HUAWEI_MBXP_PINS), SND_PCI_QUIRK(0x1b7d, 0xa831, "Ordissimo EVE2 ", ALC269VB_FIXUP_ORDISSIMO_EVE2), /* Also known as Malata PC-B1303 */ @@ -8175,8 +8175,7 @@ static const struct snd_pci_quirk alc861_fixup_tbl[] = { SND_PCI_QUIRK(0x1043, 0x1393, "ASUS A6Rp", ALC861_FIXUP_ASUS_A6RP), SND_PCI_QUIRK_VENDOR(0x1043, "ASUS laptop", ALC861_FIXUP_AMP_VREF_0F), SND_PCI_QUIRK(0x1462, 0x7254, "HP DX2200", ALC861_FIXUP_NO_JACK_DETECT), - SND_PCI_QUIRK(0x1584, 0x2b01, "Haier W18", ALC861_FIXUP_AMP_VREF_0F), - SND_PCI_QUIRK(0x1584, 0x0000, "Uniwill ECS M31EI", ALC861_FIXUP_AMP_VREF_0F), + SND_PCI_QUIRK_VENDOR(0x1584, "Haier/Uniwill", ALC861_FIXUP_AMP_VREF_0F), SND_PCI_QUIRK(0x1734, 0x10c7, "FSC Amilo Pi1505", ALC861_FIXUP_FSC_AMILO_PI1505), {} }; diff --git a/sound/pci/rme9652/hdsp.c b/sound/pci/rme9652/hdsp.c index ba99ff0e93e03..a0797fc17d957 100644 --- a/sound/pci/rme9652/hdsp.c +++ b/sound/pci/rme9652/hdsp.c @@ -5343,7 +5343,8 @@ static int snd_hdsp_free(struct hdsp *hdsp) if (hdsp->port) pci_release_regions(hdsp->pci); - pci_disable_device(hdsp->pci); + if (pci_is_enabled(hdsp->pci)) + pci_disable_device(hdsp->pci); return 0; } diff --git a/sound/pci/rme9652/hdspm.c b/sound/pci/rme9652/hdspm.c index 11b5b5e0e0580..5dfddade1bae9 100644 --- a/sound/pci/rme9652/hdspm.c +++ b/sound/pci/rme9652/hdspm.c @@ -6913,7 +6913,8 @@ static int snd_hdspm_free(struct hdspm * hdspm) if (hdspm->port) pci_release_regions(hdspm->pci); - pci_disable_device(hdspm->pci); + if (pci_is_enabled(hdspm->pci)) + pci_disable_device(hdspm->pci); return 0; } diff --git a/sound/pci/rme9652/rme9652.c b/sound/pci/rme9652/rme9652.c index edd765e223770..f82fa5be7d337 100644 --- a/sound/pci/rme9652/rme9652.c +++ b/sound/pci/rme9652/rme9652.c @@ -1761,7 +1761,8 @@ static int snd_rme9652_free(struct snd_rme9652 *rme9652) if (rme9652->port) pci_release_regions(rme9652->pci); - pci_disable_device(rme9652->pci); + if (pci_is_enabled(rme9652->pci)) + pci_disable_device(rme9652->pci); return 0; } diff --git a/sound/soc/codecs/ak5558.c b/sound/soc/codecs/ak5558.c index 73c418517f8d4..dda165b142225 100644 --- a/sound/soc/codecs/ak5558.c +++ b/sound/soc/codecs/ak5558.c @@ -271,7 +271,7 @@ static void ak5558_power_off(struct ak5558_priv *ak5558) if (!ak5558->reset_gpiod) return; - gpiod_set_value_cansleep(ak5558->reset_gpiod, 0); + gpiod_set_value_cansleep(ak5558->reset_gpiod, 1); usleep_range(1000, 2000); } @@ -280,7 +280,7 @@ static void ak5558_power_on(struct ak5558_priv *ak5558) if (!ak5558->reset_gpiod) return; - gpiod_set_value_cansleep(ak5558->reset_gpiod, 1); + gpiod_set_value_cansleep(ak5558->reset_gpiod, 0); usleep_range(1000, 2000); } diff --git a/sound/soc/codecs/rt286.c b/sound/soc/codecs/rt286.c index 0b0f748bffbe7..c29c6cf41ece6 100644 --- a/sound/soc/codecs/rt286.c +++ b/sound/soc/codecs/rt286.c @@ -174,6 +174,9 @@ static bool rt286_readable_register(struct device *dev, unsigned int reg) case RT286_PROC_COEF: case RT286_SET_AMP_GAIN_ADC_IN1: case RT286_SET_AMP_GAIN_ADC_IN2: + case RT286_SET_GPIO_MASK: + case RT286_SET_GPIO_DIRECTION: + case RT286_SET_GPIO_DATA: case RT286_SET_POWER(RT286_DAC_OUT1): case RT286_SET_POWER(RT286_DAC_OUT2): case RT286_SET_POWER(RT286_ADC_IN1): @@ -1118,12 +1121,11 @@ static const struct dmi_system_id force_combo_jack_table[] = { { } }; -static const struct dmi_system_id dmi_dell_dino[] = { +static const struct dmi_system_id dmi_dell[] = { { - .ident = "Dell Dino", + .ident = "Dell", .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Dell Inc."), - DMI_MATCH(DMI_PRODUCT_NAME, "XPS 13 9343") } }, { } @@ -1134,7 +1136,7 @@ static int rt286_i2c_probe(struct i2c_client *i2c, { struct rt286_platform_data *pdata = dev_get_platdata(&i2c->dev); struct rt286_priv *rt286; - int i, ret, val; + int i, ret, vendor_id; rt286 = devm_kzalloc(&i2c->dev, sizeof(*rt286), GFP_KERNEL); @@ -1150,14 +1152,15 @@ static int rt286_i2c_probe(struct i2c_client *i2c, } ret = regmap_read(rt286->regmap, - RT286_GET_PARAM(AC_NODE_ROOT, AC_PAR_VENDOR_ID), &val); + RT286_GET_PARAM(AC_NODE_ROOT, AC_PAR_VENDOR_ID), &vendor_id); if (ret != 0) { dev_err(&i2c->dev, "I2C error %d\n", ret); return ret; } - if (val != RT286_VENDOR_ID && val != RT288_VENDOR_ID) { + if (vendor_id != RT286_VENDOR_ID && vendor_id != RT288_VENDOR_ID) { dev_err(&i2c->dev, - "Device with ID register %#x is not rt286\n", val); + "Device with ID register %#x is not rt286\n", + vendor_id); return -ENODEV; } @@ -1181,8 +1184,8 @@ static int rt286_i2c_probe(struct i2c_client *i2c, if (pdata) rt286->pdata = *pdata; - if (dmi_check_system(force_combo_jack_table) || - dmi_check_system(dmi_dell_dino)) + if ((vendor_id == RT288_VENDOR_ID && dmi_check_system(dmi_dell)) || + dmi_check_system(force_combo_jack_table)) rt286->pdata.cbj_en = true; regmap_write(rt286->regmap, RT286_SET_AUDIO_POWER, AC_PWRST_D3); @@ -1221,7 +1224,7 @@ static int rt286_i2c_probe(struct i2c_client *i2c, regmap_update_bits(rt286->regmap, RT286_DEPOP_CTRL3, 0xf777, 0x4737); regmap_update_bits(rt286->regmap, RT286_DEPOP_CTRL4, 0x00ff, 0x003f); - if (dmi_check_system(dmi_dell_dino)) { + if (vendor_id == RT288_VENDOR_ID && dmi_check_system(dmi_dell)) { regmap_update_bits(rt286->regmap, RT286_SET_GPIO_MASK, 0x40, 0x40); regmap_update_bits(rt286->regmap, diff --git a/sound/soc/intel/boards/bytcr_rt5640.c b/sound/soc/intel/boards/bytcr_rt5640.c index d63d997763845..4ebc023f1507b 100644 --- a/sound/soc/intel/boards/bytcr_rt5640.c +++ b/sound/soc/intel/boards/bytcr_rt5640.c @@ -473,6 +473,9 @@ static const struct dmi_system_id byt_rt5640_quirk_table[] = { DMI_EXACT_MATCH(DMI_PRODUCT_NAME, "T100TAF"), }, .driver_data = (void *)(BYT_RT5640_IN1_MAP | + BYT_RT5640_JD_SRC_JD2_IN4N | + BYT_RT5640_OVCD_TH_2000UA | + BYT_RT5640_OVCD_SF_0P75 | BYT_RT5640_MONO_SPEAKER | BYT_RT5640_DIFF_MIC | BYT_RT5640_SSP0_AIF2 | @@ -506,6 +509,23 @@ static const struct dmi_system_id byt_rt5640_quirk_table[] = { BYT_RT5640_SSP0_AIF1 | BYT_RT5640_MCLK_EN), }, + { + /* Chuwi Hi8 (CWI509) */ + .matches = { + DMI_MATCH(DMI_BOARD_VENDOR, "Hampoo"), + DMI_MATCH(DMI_BOARD_NAME, "BYT-PA03C"), + DMI_MATCH(DMI_SYS_VENDOR, "ilife"), + DMI_MATCH(DMI_PRODUCT_NAME, "S806"), + }, + .driver_data = (void *)(BYT_RT5640_IN1_MAP | + BYT_RT5640_JD_SRC_JD2_IN4N | + BYT_RT5640_OVCD_TH_2000UA | + BYT_RT5640_OVCD_SF_0P75 | + BYT_RT5640_MONO_SPEAKER | + BYT_RT5640_DIFF_MIC | + BYT_RT5640_SSP0_AIF1 | + BYT_RT5640_MCLK_EN), + }, { .matches = { DMI_MATCH(DMI_SYS_VENDOR, "Circuitco"), diff --git a/sound/soc/samsung/tm2_wm5110.c b/sound/soc/samsung/tm2_wm5110.c index 43332c32d7e9b..e5890485fc5e4 100644 --- a/sound/soc/samsung/tm2_wm5110.c +++ b/sound/soc/samsung/tm2_wm5110.c @@ -541,7 +541,7 @@ static int tm2_probe(struct platform_device *pdev) ret = of_parse_phandle_with_args(dev->of_node, "i2s-controller", cells_name, i, &args); - if (!args.np) { + if (ret) { dev_err(dev, "i2s-controller property parse error: %d\n", i); ret = -EINVAL; goto dai_node_put; diff --git a/sound/usb/card.c b/sound/usb/card.c index ba096cb4a53e4..ce8925e8419eb 100644 --- a/sound/usb/card.c +++ b/sound/usb/card.c @@ -189,9 +189,8 @@ static int snd_usb_create_stream(struct snd_usb_audio *chip, int ctrlif, int int ctrlif, interface); return -EINVAL; } - usb_driver_claim_interface(&usb_audio_driver, iface, (void *)-1L); - - return 0; + return usb_driver_claim_interface(&usb_audio_driver, iface, + USB_AUDIO_IFACE_UNUSED); } if ((altsd->bInterfaceClass != USB_CLASS_AUDIO && @@ -211,7 +210,8 @@ static int snd_usb_create_stream(struct snd_usb_audio *chip, int ctrlif, int int if (! snd_usb_parse_audio_interface(chip, interface)) { usb_set_interface(dev, interface, 0); /* reset the current interface */ - usb_driver_claim_interface(&usb_audio_driver, iface, (void *)-1L); + return usb_driver_claim_interface(&usb_audio_driver, iface, + USB_AUDIO_IFACE_UNUSED); } return 0; @@ -707,7 +707,7 @@ static void usb_audio_disconnect(struct usb_interface *intf) struct snd_card *card; struct list_head *p; - if (chip == (void *)-1L) + if (chip == USB_AUDIO_IFACE_UNUSED) return; card = chip->card; @@ -807,7 +807,7 @@ static int usb_audio_suspend(struct usb_interface *intf, pm_message_t message) struct usb_mixer_interface *mixer; struct list_head *p; - if (chip == (void *)-1L) + if (chip == USB_AUDIO_IFACE_UNUSED) return 0; if (!chip->num_suspended_intf++) { @@ -839,7 +839,7 @@ static int __usb_audio_resume(struct usb_interface *intf, bool reset_resume) struct list_head *p; int err = 0; - if (chip == (void *)-1L) + if (chip == USB_AUDIO_IFACE_UNUSED) return 0; atomic_inc(&chip->active); /* avoid autopm */ diff --git a/sound/usb/clock.c b/sound/usb/clock.c index 54818658d0217..863ac42076e55 100644 --- a/sound/usb/clock.c +++ b/sound/usb/clock.c @@ -273,7 +273,7 @@ static int __uac_clock_find_source(struct snd_usb_audio *chip, selector = snd_usb_find_clock_selector(chip->ctrl_intf, entity_id); if (selector) { - int ret, i, cur; + int ret, i, cur, err; /* the entity ID we are looking for is a selector. * find out what it currently selects */ @@ -295,13 +295,17 @@ static int __uac_clock_find_source(struct snd_usb_audio *chip, ret = __uac_clock_find_source(chip, fmt, selector->baCSourceID[ret - 1], visited, validate); + if (ret > 0) { + err = uac_clock_selector_set_val(chip, entity_id, cur); + if (err < 0) + return err; + } + if (!validate || ret > 0 || !chip->autoclock) return ret; /* The current clock source is invalid, try others. */ for (i = 1; i <= selector->bNrInPins; i++) { - int err; - if (i == cur) continue; @@ -367,7 +371,7 @@ static int __uac3_clock_find_source(struct snd_usb_audio *chip, selector = snd_usb_find_clock_selector_v3(chip->ctrl_intf, entity_id); if (selector) { - int ret, i, cur; + int ret, i, cur, err; /* the entity ID we are looking for is a selector. * find out what it currently selects */ @@ -389,6 +393,12 @@ static int __uac3_clock_find_source(struct snd_usb_audio *chip, ret = __uac3_clock_find_source(chip, fmt, selector->baCSourceID[ret - 1], visited, validate); + if (ret > 0) { + err = uac_clock_selector_set_val(chip, entity_id, cur); + if (err < 0) + return err; + } + if (!validate || ret > 0 || !chip->autoclock) return ret; diff --git a/sound/usb/midi.c b/sound/usb/midi.c index 26548f760bc1c..4553db0ef0841 100644 --- a/sound/usb/midi.c +++ b/sound/usb/midi.c @@ -1333,7 +1333,7 @@ static int snd_usbmidi_in_endpoint_create(struct snd_usb_midi *umidi, error: snd_usbmidi_in_endpoint_delete(ep); - return -ENOMEM; + return err; } /* diff --git a/sound/usb/mixer.c b/sound/usb/mixer.c index 451b8ea383c61..4ad6eeb43476b 100644 --- a/sound/usb/mixer.c +++ b/sound/usb/mixer.c @@ -1045,7 +1045,7 @@ struct usb_feature_control_info { int type_uac2; /* data type for uac2 if different from uac1, else -1 */ }; -static struct usb_feature_control_info audio_feature_info[] = { +static const struct usb_feature_control_info audio_feature_info[] = { { UAC_FU_MUTE, "Mute", USB_MIXER_INV_BOOLEAN, -1 }, { UAC_FU_VOLUME, "Volume", USB_MIXER_S16, -1 }, { UAC_FU_BASS, "Tone Control - Bass", USB_MIXER_S8, -1 }, @@ -1559,7 +1559,7 @@ static void check_no_speaker_on_headset(struct snd_kcontrol *kctl, strlcpy(kctl->id.name, "Headphone", sizeof(kctl->id.name)); } -static struct usb_feature_control_info *get_feature_control_info(int control) +static const struct usb_feature_control_info *get_feature_control_info(int control) { int i; @@ -1577,7 +1577,7 @@ static void __build_feature_ctl(struct usb_mixer_interface *mixer, struct usb_audio_term *oterm, int unitid, int nameid, int readonly_mask) { - struct usb_feature_control_info *ctl_info; + const struct usb_feature_control_info *ctl_info; unsigned int len = 0; int mapped_name = 0; struct snd_kcontrol *kctl; @@ -2256,7 +2256,7 @@ static const struct snd_kcontrol_new mixer_procunit_ctl = { */ struct procunit_value_info { int control; - char *suffix; + const char *suffix; int val_type; int min_value; }; @@ -2264,44 +2264,44 @@ struct procunit_value_info { struct procunit_info { int type; char *name; - struct procunit_value_info *values; + const struct procunit_value_info *values; }; -static struct procunit_value_info undefined_proc_info[] = { +static const struct procunit_value_info undefined_proc_info[] = { { 0x00, "Control Undefined", 0 }, { 0 } }; -static struct procunit_value_info updown_proc_info[] = { +static const struct procunit_value_info updown_proc_info[] = { { UAC_UD_ENABLE, "Switch", USB_MIXER_BOOLEAN }, { UAC_UD_MODE_SELECT, "Mode Select", USB_MIXER_U8, 1 }, { 0 } }; -static struct procunit_value_info prologic_proc_info[] = { +static const struct procunit_value_info prologic_proc_info[] = { { UAC_DP_ENABLE, "Switch", USB_MIXER_BOOLEAN }, { UAC_DP_MODE_SELECT, "Mode Select", USB_MIXER_U8, 1 }, { 0 } }; -static struct procunit_value_info threed_enh_proc_info[] = { +static const struct procunit_value_info threed_enh_proc_info[] = { { UAC_3D_ENABLE, "Switch", USB_MIXER_BOOLEAN }, { UAC_3D_SPACE, "Spaciousness", USB_MIXER_U8 }, { 0 } }; -static struct procunit_value_info reverb_proc_info[] = { +static const struct procunit_value_info reverb_proc_info[] = { { UAC_REVERB_ENABLE, "Switch", USB_MIXER_BOOLEAN }, { UAC_REVERB_LEVEL, "Level", USB_MIXER_U8 }, { UAC_REVERB_TIME, "Time", USB_MIXER_U16 }, { UAC_REVERB_FEEDBACK, "Feedback", USB_MIXER_U8 }, { 0 } }; -static struct procunit_value_info chorus_proc_info[] = { +static const struct procunit_value_info chorus_proc_info[] = { { UAC_CHORUS_ENABLE, "Switch", USB_MIXER_BOOLEAN }, { UAC_CHORUS_LEVEL, "Level", USB_MIXER_U8 }, { UAC_CHORUS_RATE, "Rate", USB_MIXER_U16 }, { UAC_CHORUS_DEPTH, "Depth", USB_MIXER_U16 }, { 0 } }; -static struct procunit_value_info dcr_proc_info[] = { +static const struct procunit_value_info dcr_proc_info[] = { { UAC_DCR_ENABLE, "Switch", USB_MIXER_BOOLEAN }, { UAC_DCR_RATE, "Ratio", USB_MIXER_U16 }, { UAC_DCR_MAXAMPL, "Max Amp", USB_MIXER_S16 }, @@ -2311,7 +2311,7 @@ static struct procunit_value_info dcr_proc_info[] = { { 0 } }; -static struct procunit_info procunits[] = { +static const struct procunit_info procunits[] = { { UAC_PROCESS_UP_DOWNMIX, "Up Down", updown_proc_info }, { UAC_PROCESS_DOLBY_PROLOGIC, "Dolby Prologic", prologic_proc_info }, { UAC_PROCESS_STEREO_EXTENDER, "3D Stereo Extender", threed_enh_proc_info }, @@ -2321,16 +2321,16 @@ static struct procunit_info procunits[] = { { 0 }, }; -static struct procunit_value_info uac3_updown_proc_info[] = { +static const struct procunit_value_info uac3_updown_proc_info[] = { { UAC3_UD_MODE_SELECT, "Mode Select", USB_MIXER_U8, 1 }, { 0 } }; -static struct procunit_value_info uac3_stereo_ext_proc_info[] = { +static const struct procunit_value_info uac3_stereo_ext_proc_info[] = { { UAC3_EXT_WIDTH_CONTROL, "Width Control", USB_MIXER_U8 }, { 0 } }; -static struct procunit_info uac3_procunits[] = { +static const struct procunit_info uac3_procunits[] = { { UAC3_PROCESS_UP_DOWNMIX, "Up Down", uac3_updown_proc_info }, { UAC3_PROCESS_STEREO_EXTENDER, "3D Stereo Extender", uac3_stereo_ext_proc_info }, { UAC3_PROCESS_MULTI_FUNCTION, "Multi-Function", undefined_proc_info }, @@ -2340,23 +2340,23 @@ static struct procunit_info uac3_procunits[] = { /* * predefined data for extension units */ -static struct procunit_value_info clock_rate_xu_info[] = { +static const struct procunit_value_info clock_rate_xu_info[] = { { USB_XU_CLOCK_RATE_SELECTOR, "Selector", USB_MIXER_U8, 0 }, { 0 } }; -static struct procunit_value_info clock_source_xu_info[] = { +static const struct procunit_value_info clock_source_xu_info[] = { { USB_XU_CLOCK_SOURCE_SELECTOR, "External", USB_MIXER_BOOLEAN }, { 0 } }; -static struct procunit_value_info spdif_format_xu_info[] = { +static const struct procunit_value_info spdif_format_xu_info[] = { { USB_XU_DIGITAL_FORMAT_SELECTOR, "SPDIF/AC3", USB_MIXER_BOOLEAN }, { 0 } }; -static struct procunit_value_info soft_limit_xu_info[] = { +static const struct procunit_value_info soft_limit_xu_info[] = { { USB_XU_SOFT_LIMIT_SELECTOR, " ", USB_MIXER_BOOLEAN }, { 0 } }; -static struct procunit_info extunits[] = { +static const struct procunit_info extunits[] = { { USB_XU_CLOCK_RATE, "Clock rate", clock_rate_xu_info }, { USB_XU_CLOCK_SOURCE, "DigitalIn CLK source", clock_source_xu_info }, { USB_XU_DIGITAL_IO_STATUS, "DigitalOut format:", spdif_format_xu_info }, @@ -2368,7 +2368,7 @@ static struct procunit_info extunits[] = { * build a processing/extension unit */ static int build_audio_procunit(struct mixer_build *state, int unitid, - void *raw_desc, struct procunit_info *list, + void *raw_desc, const struct procunit_info *list, bool extension_unit) { struct uac_processing_unit_descriptor *desc = raw_desc; @@ -2376,14 +2376,14 @@ static int build_audio_procunit(struct mixer_build *state, int unitid, struct usb_mixer_elem_info *cval; struct snd_kcontrol *kctl; int i, err, nameid, type, len; - struct procunit_info *info; - struct procunit_value_info *valinfo; + const struct procunit_info *info; + const struct procunit_value_info *valinfo; const struct usbmix_name_map *map; - static struct procunit_value_info default_value_info[] = { + static const struct procunit_value_info default_value_info[] = { { 0x01, "Switch", USB_MIXER_BOOLEAN }, { 0 } }; - static struct procunit_info default_info = { + static const struct procunit_info default_info = { 0, NULL, default_value_info }; const char *name = extension_unit ? @@ -2861,7 +2861,7 @@ struct uac3_badd_profile { int st_chmask; /* side tone mixing channel mask */ }; -static struct uac3_badd_profile uac3_badd_profiles[] = { +static const struct uac3_badd_profile uac3_badd_profiles[] = { { /* * BAIF, BAOF or combination of both @@ -2922,7 +2922,7 @@ static struct uac3_badd_profile uac3_badd_profiles[] = { }; static bool uac3_badd_func_has_valid_channels(struct usb_mixer_interface *mixer, - struct uac3_badd_profile *f, + const struct uac3_badd_profile *f, int c_chmask, int p_chmask) { /* @@ -2966,7 +2966,7 @@ static int snd_usb_mixer_controls_badd(struct usb_mixer_interface *mixer, struct usb_device *dev = mixer->chip->dev; struct usb_interface_assoc_descriptor *assoc; int badd_profile = mixer->chip->badd_profile; - struct uac3_badd_profile *f; + const struct uac3_badd_profile *f; const struct usbmix_ctl_map *map; int p_chmask = 0, c_chmask = 0, st_chmask = 0; int i; @@ -3260,7 +3260,7 @@ static void snd_usb_mixer_dump_cval(struct snd_info_buffer *buffer, struct usb_mixer_elem_list *list) { struct usb_mixer_elem_info *cval = mixer_elem_list_to_info(list); - static char *val_types[] = {"BOOLEAN", "INV_BOOLEAN", + static const char * const val_types[] = {"BOOLEAN", "INV_BOOLEAN", "S8", "U8", "S16", "U16"}; snd_iprintf(buffer, " Info: id=%i, control=%i, cmask=0x%x, " "channels=%i, type=\"%s\"\n", cval->head.id, diff --git a/sound/usb/mixer_maps.c b/sound/usb/mixer_maps.c index 10323e6f7f97e..1d4e535e2c117 100644 --- a/sound/usb/mixer_maps.c +++ b/sound/usb/mixer_maps.c @@ -28,7 +28,7 @@ struct usbmix_name_map { int id; const char *name; int control; - struct usbmix_dB_map *dB; + const struct usbmix_dB_map *dB; }; struct usbmix_selector_map { @@ -67,7 +67,7 @@ Mic-IN[9] --+->FU[10]----------------------------+ | ++--+->SU[11]-->FU[12] --------------------------------------------------------------------------------------> USB_OUT[13] */ -static struct usbmix_name_map extigy_map[] = { +static const struct usbmix_name_map extigy_map[] = { /* 1: IT pcm */ { 2, "PCM Playback" }, /* FU */ /* 3: IT pcm */ @@ -108,12 +108,12 @@ static struct usbmix_name_map extigy_map[] = { * e.g. no Master and fake PCM volume * Pavel Mihaylov */ -static struct usbmix_dB_map mp3plus_dB_1 = {.min = -4781, .max = 0}; +static const struct usbmix_dB_map mp3plus_dB_1 = {.min = -4781, .max = 0}; /* just guess */ -static struct usbmix_dB_map mp3plus_dB_2 = {.min = -1781, .max = 618}; +static const struct usbmix_dB_map mp3plus_dB_2 = {.min = -1781, .max = 618}; /* just guess */ -static struct usbmix_name_map mp3plus_map[] = { +static const struct usbmix_name_map mp3plus_map[] = { /* 1: IT pcm */ /* 2: IT mic */ /* 3: IT line */ @@ -154,7 +154,7 @@ Lin_IN[7]-+--->FU[8]---+ +->EU[23]->FU[28]------------->Spk_OUT[19] | ^ +->FU[13]--------------------------------------+ */ -static struct usbmix_name_map audigy2nx_map[] = { +static const struct usbmix_name_map audigy2nx_map[] = { /* 1: IT pcm playback */ /* 4: IT digital in */ { 6, "Digital In Playback" }, /* FU */ @@ -182,12 +182,12 @@ static struct usbmix_name_map audigy2nx_map[] = { { 0 } /* terminator */ }; -static struct usbmix_name_map mbox1_map[] = { +static const struct usbmix_name_map mbox1_map[] = { { 1, "Clock" }, { 0 } /* terminator */ }; -static struct usbmix_selector_map c400_selectors[] = { +static const struct usbmix_selector_map c400_selectors[] = { { .id = 0x80, .count = 2, @@ -196,7 +196,7 @@ static struct usbmix_selector_map c400_selectors[] = { { 0 } /* terminator */ }; -static struct usbmix_selector_map audigy2nx_selectors[] = { +static const struct usbmix_selector_map audigy2nx_selectors[] = { { .id = 14, /* Capture Source */ .count = 3, @@ -216,21 +216,21 @@ static struct usbmix_selector_map audigy2nx_selectors[] = { }; /* Creative SoundBlaster Live! 24-bit External */ -static struct usbmix_name_map live24ext_map[] = { +static const struct usbmix_name_map live24ext_map[] = { /* 2: PCM Playback Volume */ { 5, "Mic Capture" }, /* FU, default PCM Capture Volume */ { 0 } /* terminator */ }; /* LineX FM Transmitter entry - needed to bypass controls bug */ -static struct usbmix_name_map linex_map[] = { +static const struct usbmix_name_map linex_map[] = { /* 1: IT pcm */ /* 2: OT Speaker */ { 3, "Master" }, /* FU: master volume - left / right / mute */ { 0 } /* terminator */ }; -static struct usbmix_name_map maya44_map[] = { +static const struct usbmix_name_map maya44_map[] = { /* 1: IT line */ { 2, "Line Playback" }, /* FU */ /* 3: IT line */ @@ -253,7 +253,7 @@ static struct usbmix_name_map maya44_map[] = { * so this map removes all unwanted sliders from alsamixer */ -static struct usbmix_name_map justlink_map[] = { +static const struct usbmix_name_map justlink_map[] = { /* 1: IT pcm playback */ /* 2: Not present */ { 3, NULL}, /* IT mic (No mic input on device) */ @@ -270,7 +270,7 @@ static struct usbmix_name_map justlink_map[] = { }; /* TerraTec Aureon 5.1 MkII USB */ -static struct usbmix_name_map aureon_51_2_map[] = { +static const struct usbmix_name_map aureon_51_2_map[] = { /* 1: IT USB */ /* 2: IT Mic */ /* 3: IT Line */ @@ -289,7 +289,7 @@ static struct usbmix_name_map aureon_51_2_map[] = { {} /* terminator */ }; -static struct usbmix_name_map scratch_live_map[] = { +static const struct usbmix_name_map scratch_live_map[] = { /* 1: IT Line 1 (USB streaming) */ /* 2: OT Line 1 (Speaker) */ /* 3: IT Line 1 (Line connector) */ @@ -305,7 +305,7 @@ static struct usbmix_name_map scratch_live_map[] = { { 0 } /* terminator */ }; -static struct usbmix_name_map ebox44_map[] = { +static const struct usbmix_name_map ebox44_map[] = { { 4, NULL }, /* FU */ { 6, NULL }, /* MU */ { 7, NULL }, /* FU */ @@ -320,7 +320,7 @@ static struct usbmix_name_map ebox44_map[] = { * FIXME: or mp3plus_map should use "Capture Source" too, * so this maps can be merget */ -static struct usbmix_name_map hercules_usb51_map[] = { +static const struct usbmix_name_map hercules_usb51_map[] = { { 8, "Capture Source" }, /* SU, default "PCM Capture Source" */ { 9, "Master Playback" }, /* FU, default "Speaker Playback" */ { 10, "Mic Boost", 7 }, /* FU, default "Auto Gain Input" */ @@ -331,7 +331,7 @@ static struct usbmix_name_map hercules_usb51_map[] = { }; /* Plantronics Gamecom 780 has a broken volume control, better to disable it */ -static struct usbmix_name_map gamecom780_map[] = { +static const struct usbmix_name_map gamecom780_map[] = { { 9, NULL }, /* FU, speaker out */ {} }; @@ -345,12 +345,19 @@ static const struct usbmix_name_map scms_usb3318_map[] = { }; /* Bose companion 5, the dB conversion factor is 16 instead of 256 */ -static struct usbmix_dB_map bose_companion5_dB = {-5006, -6}; -static struct usbmix_name_map bose_companion5_map[] = { +static const struct usbmix_dB_map bose_companion5_dB = {-5006, -6}; +static const struct usbmix_name_map bose_companion5_map[] = { { 3, NULL, .dB = &bose_companion5_dB }, { 0 } /* terminator */ }; +/* Sennheiser Communications Headset [PC 8], the dB value is reported as -6 negative maximum */ +static const struct usbmix_dB_map sennheiser_pc8_dB = {-9500, 0}; +static const struct usbmix_name_map sennheiser_pc8_map[] = { + { 9, NULL, .dB = &sennheiser_pc8_dB }, + { 0 } /* terminator */ +}; + /* * Dell usb dock with ALC4020 codec had a firmware problem where it got * screwed up when zero volume is passed; just skip it as a workaround @@ -420,7 +427,7 @@ static const struct usbmix_name_map aorus_master_alc1220vb_map[] = { * Control map entries */ -static struct usbmix_ctl_map usbmix_ctl_maps[] = { +static const struct usbmix_ctl_map usbmix_ctl_maps[] = { { .id = USB_ID(0x041e, 0x3000), .map = extigy_map, @@ -574,37 +581,37 @@ static struct usbmix_ctl_map usbmix_ctl_maps[] = { * Control map entries for UAC3 BADD profiles */ -static struct usbmix_name_map uac3_badd_generic_io_map[] = { +static const struct usbmix_name_map uac3_badd_generic_io_map[] = { { UAC3_BADD_FU_ID2, "Generic Out Playback" }, { UAC3_BADD_FU_ID5, "Generic In Capture" }, { 0 } /* terminator */ }; -static struct usbmix_name_map uac3_badd_headphone_map[] = { +static const struct usbmix_name_map uac3_badd_headphone_map[] = { { UAC3_BADD_FU_ID2, "Headphone Playback" }, { 0 } /* terminator */ }; -static struct usbmix_name_map uac3_badd_speaker_map[] = { +static const struct usbmix_name_map uac3_badd_speaker_map[] = { { UAC3_BADD_FU_ID2, "Speaker Playback" }, { 0 } /* terminator */ }; -static struct usbmix_name_map uac3_badd_microphone_map[] = { +static const struct usbmix_name_map uac3_badd_microphone_map[] = { { UAC3_BADD_FU_ID5, "Mic Capture" }, { 0 } /* terminator */ }; /* Covers also 'headset adapter' profile */ -static struct usbmix_name_map uac3_badd_headset_map[] = { +static const struct usbmix_name_map uac3_badd_headset_map[] = { { UAC3_BADD_FU_ID2, "Headset Playback" }, { UAC3_BADD_FU_ID5, "Headset Capture" }, { UAC3_BADD_FU_ID7, "Sidetone Mixing" }, { 0 } /* terminator */ }; -static struct usbmix_name_map uac3_badd_speakerphone_map[] = { +static const struct usbmix_name_map uac3_badd_speakerphone_map[] = { { UAC3_BADD_FU_ID2, "Speaker Playback" }, { UAC3_BADD_FU_ID5, "Mic Capture" }, { 0 } /* terminator */ }; -static struct usbmix_ctl_map uac3_badd_usbmix_ctl_maps[] = { +static const struct usbmix_ctl_map uac3_badd_usbmix_ctl_maps[] = { { .id = UAC3_FUNCTION_SUBCLASS_GENERIC_IO, .map = uac3_badd_generic_io_map, @@ -633,5 +640,10 @@ static struct usbmix_ctl_map uac3_badd_usbmix_ctl_maps[] = { .id = UAC3_FUNCTION_SUBCLASS_SPEAKERPHONE, .map = uac3_badd_speakerphone_map, }, + { + /* Sennheiser Communications Headset [PC 8] */ + .id = USB_ID(0x1395, 0x0025), + .map = sennheiser_pc8_map, + }, { 0 } /* terminator */ }; diff --git a/sound/usb/mixer_quirks.c b/sound/usb/mixer_quirks.c index d1328abd1bc49..169679419b398 100644 --- a/sound/usb/mixer_quirks.c +++ b/sound/usb/mixer_quirks.c @@ -130,7 +130,7 @@ static int snd_create_std_mono_ctl(struct usb_mixer_interface *mixer, * Create a set of standard UAC controls from a table */ static int snd_create_std_mono_table(struct usb_mixer_interface *mixer, - struct std_mono_table *t) + const struct std_mono_table *t) { int err; @@ -1399,7 +1399,7 @@ static int snd_c400_create_mixer(struct usb_mixer_interface *mixer) * are valid they presents mono controls as L and R channels of * stereo. So we provide a good mixer here. */ -static struct std_mono_table ebox44_table[] = { +static const struct std_mono_table ebox44_table[] = { { .unitid = 4, .control = 1, @@ -1708,7 +1708,7 @@ static struct snd_kcontrol_new snd_microii_mixer_spdif[] = { static int snd_microii_controls_create(struct usb_mixer_interface *mixer) { int err, i; - static usb_mixer_elem_resume_func_t resume_funcs[] = { + const static usb_mixer_elem_resume_func_t resume_funcs[] = { snd_microii_spdif_default_update, NULL, snd_microii_spdif_switch_update diff --git a/sound/usb/mixer_scarlett.c b/sound/usb/mixer_scarlett.c index 4aeb9488a0c99..2e93c0b2e8e32 100644 --- a/sound/usb/mixer_scarlett.c +++ b/sound/usb/mixer_scarlett.c @@ -633,7 +633,7 @@ static int add_output_ctls(struct usb_mixer_interface *mixer, /********************** device-specific config *************************/ /* untested... */ -static struct scarlett_device_info s6i6_info = { +static const struct scarlett_device_info s6i6_info = { .matrix_in = 18, .matrix_out = 8, .input_len = 6, @@ -675,7 +675,7 @@ static struct scarlett_device_info s6i6_info = { }; /* untested... */ -static struct scarlett_device_info s8i6_info = { +static const struct scarlett_device_info s8i6_info = { .matrix_in = 18, .matrix_out = 6, .input_len = 8, @@ -714,7 +714,7 @@ static struct scarlett_device_info s8i6_info = { } }; -static struct scarlett_device_info s18i6_info = { +static const struct scarlett_device_info s18i6_info = { .matrix_in = 18, .matrix_out = 6, .input_len = 18, @@ -751,7 +751,7 @@ static struct scarlett_device_info s18i6_info = { } }; -static struct scarlett_device_info s18i8_info = { +static const struct scarlett_device_info s18i8_info = { .matrix_in = 18, .matrix_out = 8, .input_len = 18, @@ -793,7 +793,7 @@ static struct scarlett_device_info s18i8_info = { } }; -static struct scarlett_device_info s18i20_info = { +static const struct scarlett_device_info s18i20_info = { .matrix_in = 18, .matrix_out = 8, .input_len = 18, @@ -843,7 +843,7 @@ static struct scarlett_device_info s18i20_info = { static int scarlett_controls_create_generic(struct usb_mixer_interface *mixer, - struct scarlett_device_info *info) + const struct scarlett_device_info *info) { int i, err; char mx[SNDRV_CTL_ELEM_ID_NAME_MAXLEN]; @@ -906,7 +906,7 @@ int snd_scarlett_controls_create(struct usb_mixer_interface *mixer) { int err, i, o; char mx[SNDRV_CTL_ELEM_ID_NAME_MAXLEN]; - struct scarlett_device_info *info; + const struct scarlett_device_info *info; struct usb_mixer_elem_info *elem; static char sample_rate_buffer[4] = { '\x80', '\xbb', '\x00', '\x00' }; diff --git a/sound/usb/proc.c b/sound/usb/proc.c index 0ac89e294d31d..28192b0b25481 100644 --- a/sound/usb/proc.c +++ b/sound/usb/proc.c @@ -74,7 +74,7 @@ void snd_usb_audio_create_proc(struct snd_usb_audio *chip) static void proc_dump_substream_formats(struct snd_usb_substream *subs, struct snd_info_buffer *buffer) { struct audioformat *fp; - static char *sync_types[4] = { + static const char * const sync_types[4] = { "NONE", "ASYNC", "ADAPTIVE", "SYNC" }; diff --git a/sound/usb/quirks.c b/sound/usb/quirks.c index 717edf3b5d3e3..b5f2b18b8b422 100644 --- a/sound/usb/quirks.c +++ b/sound/usb/quirks.c @@ -66,8 +66,12 @@ static int create_composite_quirk(struct snd_usb_audio *chip, if (!iface) continue; if (quirk->ifnum != probed_ifnum && - !usb_interface_claimed(iface)) - usb_driver_claim_interface(driver, iface, (void *)-1L); + !usb_interface_claimed(iface)) { + err = usb_driver_claim_interface(driver, iface, + USB_AUDIO_IFACE_UNUSED); + if (err < 0) + return err; + } } return 0; @@ -401,8 +405,12 @@ static int create_autodetect_quirks(struct snd_usb_audio *chip, continue; err = create_autodetect_quirk(chip, iface, driver); - if (err >= 0) - usb_driver_claim_interface(driver, iface, (void *)-1L); + if (err >= 0) { + err = usb_driver_claim_interface(driver, iface, + USB_AUDIO_IFACE_UNUSED); + if (err < 0) + return err; + } } return 0; diff --git a/sound/usb/stream.c b/sound/usb/stream.c index 94bef3d043786..9a950aaf5e356 100644 --- a/sound/usb/stream.c +++ b/sound/usb/stream.c @@ -245,7 +245,7 @@ static int add_chmap(struct snd_pcm *pcm, int stream, static struct snd_pcm_chmap_elem *convert_chmap(int channels, unsigned int bits, int protocol) { - static unsigned int uac1_maps[] = { + static const unsigned int uac1_maps[] = { SNDRV_CHMAP_FL, /* left front */ SNDRV_CHMAP_FR, /* right front */ SNDRV_CHMAP_FC, /* center front */ @@ -260,7 +260,7 @@ static struct snd_pcm_chmap_elem *convert_chmap(int channels, unsigned int bits, SNDRV_CHMAP_TC, /* top */ 0 /* terminator */ }; - static unsigned int uac2_maps[] = { + static const unsigned int uac2_maps[] = { SNDRV_CHMAP_FL, /* front left */ SNDRV_CHMAP_FR, /* front right */ SNDRV_CHMAP_FC, /* front center */ diff --git a/sound/usb/usbaudio.h b/sound/usb/usbaudio.h index 0d620c267e7a3..0c7ea78317fca 100644 --- a/sound/usb/usbaudio.h +++ b/sound/usb/usbaudio.h @@ -68,6 +68,8 @@ struct snd_usb_audio { struct usb_host_interface *ctrl_intf; /* the audio control interface */ }; +#define USB_AUDIO_IFACE_UNUSED ((void *)-1L) + #define usb_audio_err(chip, fmt, args...) \ dev_err(&(chip)->dev->dev, fmt, ##args) #define usb_audio_warn(chip, fmt, args...) \ diff --git a/sound/usb/validate.c b/sound/usb/validate.c index 5a3c4f7882b00..89a48d7317199 100644 --- a/sound/usb/validate.c +++ b/sound/usb/validate.c @@ -233,7 +233,7 @@ static bool validate_midi_out_jack(const void *p, #define FIXED(p, t, s) { .protocol = (p), .type = (t), .size = sizeof(s) } #define FUNC(p, t, f) { .protocol = (p), .type = (t), .func = (f) } -static struct usb_desc_validator audio_validators[] = { +static const struct usb_desc_validator audio_validators[] = { /* UAC1 */ FUNC(UAC_VERSION_1, UAC_HEADER, validate_uac1_header), FIXED(UAC_VERSION_1, UAC_INPUT_TERMINAL, @@ -288,7 +288,7 @@ static struct usb_desc_validator audio_validators[] = { { } /* terminator */ }; -static struct usb_desc_validator midi_validators[] = { +static const struct usb_desc_validator midi_validators[] = { FIXED(UAC_VERSION_ALL, USB_MS_HEADER, struct usb_ms_header_descriptor), FIXED(UAC_VERSION_ALL, USB_MS_MIDI_IN_JACK, diff --git a/tools/perf/python/tracepoint.py b/tools/perf/python/tracepoint.py index eb76f6516247e..461848c7f57dc 100755 --- a/tools/perf/python/tracepoint.py +++ b/tools/perf/python/tracepoint.py @@ -1,4 +1,4 @@ -#! /usr/bin/python +#! /usr/bin/env python # SPDX-License-Identifier: GPL-2.0 # -*- python -*- # -*- coding: utf-8 -*- diff --git a/tools/perf/util/symbol_fprintf.c b/tools/perf/util/symbol_fprintf.c index ed0205cc79426..1fd175bb46004 100644 --- a/tools/perf/util/symbol_fprintf.c +++ b/tools/perf/util/symbol_fprintf.c @@ -66,7 +66,7 @@ size_t dso__fprintf_symbols_by_name(struct dso *dso, for (nd = rb_first(&dso->symbol_names); nd; nd = rb_next(nd)) { pos = rb_entry(nd, struct symbol_name_rb_node, rb_node); - fprintf(fp, "%s\n", pos->sym.name); + ret += fprintf(fp, "%s\n", pos->sym.name); } return ret; diff --git a/tools/testing/ktest/compare-ktest-sample.pl b/tools/testing/ktest/compare-ktest-sample.pl index 4118eb4a842d2..ebea21d0a1be8 100755 --- a/tools/testing/ktest/compare-ktest-sample.pl +++ b/tools/testing/ktest/compare-ktest-sample.pl @@ -1,4 +1,4 @@ -#!/usr/bin/perl +#!/usr/bin/env perl # SPDX-License-Identifier: GPL-2.0 open (IN,"ktest.pl"); diff --git a/tools/testing/selftests/bpf/test_offload.py b/tools/testing/selftests/bpf/test_offload.py index 2229e55216a97..6b46db61c6d3f 100755 --- a/tools/testing/selftests/bpf/test_offload.py +++ b/tools/testing/selftests/bpf/test_offload.py @@ -1,4 +1,4 @@ -#!/usr/bin/python3 +#!/usr/bin/env python3 # Copyright (C) 2017 Netronome Systems, Inc. # diff --git a/tools/testing/selftests/lib.mk b/tools/testing/selftests/lib.mk index 0ef203ec59fdc..a5d40653a9211 100644 --- a/tools/testing/selftests/lib.mk +++ b/tools/testing/selftests/lib.mk @@ -1,6 +1,10 @@ # This mimics the top-level Makefile. We do it explicitly here so that this # Makefile can operate with or without the kbuild infrastructure. +ifneq ($(LLVM),) +CC := clang +else CC := $(CROSS_COMPILE)gcc +endif ifeq (0,$(MAKELEVEL)) OUTPUT := $(shell pwd) diff --git a/tools/testing/selftests/tc-testing/tdc_batch.py b/tools/testing/selftests/tc-testing/tdc_batch.py index 52fa539dc662b..3d8350d6bfe18 100755 --- a/tools/testing/selftests/tc-testing/tdc_batch.py +++ b/tools/testing/selftests/tc-testing/tdc_batch.py @@ -1,4 +1,4 @@ -#!/usr/bin/python3 +#!/usr/bin/env python3 """ tdc_batch.py - a script to generate TC batch file diff --git a/virt/kvm/arm/arm.c b/virt/kvm/arm/arm.c index d982650deb33f..39706799ecdf8 100644 --- a/virt/kvm/arm/arm.c +++ b/virt/kvm/arm/arm.c @@ -574,6 +574,8 @@ static int kvm_vcpu_first_run_init(struct kvm_vcpu *vcpu) vcpu->arch.has_run_once = true; + kvm_arm_vcpu_init_debug(vcpu); + if (likely(irqchip_in_kernel(kvm))) { /* * Map the VGIC hardware resources before running a vcpu the