5.15.91-rc1 review
Subsystems (6)
Greg Kroah-Hartman
maintainercover 5.15.91-rc1 review
This is the start of the stable review cycle for the 5.15.91 release. There are 204 patches in this series, all will be posted as a response to this one. If anyone has any issues with these being applied, please let me know.
Responses should be made by Wed, 01 Feb 2023 13:42:39 +0000. Anything received after that time might be too late.
The whole patch series can be found in one patch at:
https://www.kernel.org/pub/linux/kernel/v5.x/stable-review/patch-5.15.91-rc1.gz
or in the git tree and branch at:
git://git.kernel.org/pub/scm/linux/kernel/git/stable/linux-stable-rc.git linux-5.15.y
and the diffstat can be found below.
thanks,
greg k-h
-------------
Pseudo-Shortlog of commits:
Greg Kroah-Hartman <[email protected]>
Linux 5.15.91-rc1
Colin Ian King <[email protected]>
perf/x86/amd: fix potential integer overflow on shift of a int
Sriram Yagnaraman <[email protected]>
netfilter: conntrack: unify established states for SCTP paths
Thomas Gleixner <[email protected]>
x86/i8259: Mark legacy PIC interrupts with IRQ_LEVEL
Christoph Hellwig <[email protected]>
block: fix and cleanup bio_check_ro
Chun-Tse Shao <[email protected]>
kbuild: Allow kernel installation packaging to override pkg-config
Kevin Hao <[email protected]>
cpufreq: governor: Use kobject release() method to free dbs_data
Kevin Hao <[email protected]>
cpufreq: Move to_gov_attr_set() to cpufreq.h
Dmitry Torokhov <[email protected]>
Revert "Input: synaptics - switch touchpad on HP Laptop 15-da3001TU to RMI mode"
Ivo Borisov Shopov <[email protected]>
tools: gpio: fix -c option of gpio-event-mon
Linus Torvalds <[email protected]>
treewide: fix up files incorrectly marked executable
Jerome Brunet <[email protected]>
net: mdio-mux-meson-g12a: force internal PHY off on mux switch
David Christensen <[email protected]>
net/tg3: resolve deadlock in tg3_reset_task() during EEH
Rafael J. Wysocki <[email protected]>
thermal: intel: int340x: Add locking to int340x_thermal_get_trip_type()
Jeremy Kerr <[email protected]>
net: mctp: mark socks as dead on unhash, prevent re-add
Yoshihiro Shimoda <[email protected]>
net: ravb: Fix possible hang if RIS2_QFF1 happen
Yoshihiro Shimoda <[email protected]>
net: ravb: Fix lack of register setting after system resumed for Gen3
Biju Das <[email protected]>
ravb: Rename "no_ptp_cfg_active" and "ptp_cfg_active" variables
Dan Carpenter <[email protected]>
gpio: mxc: Unlock on error path in mxc_flip_edge()
Keith Busch <[email protected]>
nvme: fix passthrough csi check
Liao Chang <[email protected]>
riscv/kprobe: Fix instruction simulation of JALR
Marcelo Ricardo Leitner <[email protected]>
sctp: fail if no bound addresses can be used for a given scope
Eric Dumazet <[email protected]>
net/sched: sch_taprio: do not schedule in taprio_reset()
Kuniyuki Iwashima <[email protected]>
netrom: Fix use-after-free of a listening socket.
Sriram Yagnaraman <[email protected]>
netfilter: conntrack: fix bug in for_each_sctp_chunk
Sriram Yagnaraman <[email protected]>
netfilter: conntrack: fix vtag checks for ABORT/SHUTDOWN_COMPLETE
Eric Dumazet <[email protected]>
ipv4: prevent potential spectre v1 gadget in fib_metrics_match()
Eric Dumazet <[email protected]>
ipv4: prevent potential spectre v1 gadget in ip_metrics_convert()
Eric Dumazet <[email protected]>
netlink: annotate data races around sk_state
Eric Dumazet <[email protected]>
netlink: annotate data races around dst_portid and dst_group
Eric Dumazet <[email protected]>
netlink: annotate data races around nlk->portid
Pablo Neira Ayuso <[email protected]>
netfilter: nft_set_rbtree: skip elements in transaction from garbage collection
Pablo Neira Ayuso <[email protected]>
netfilter: nft_set_rbtree: Switch to node list walk for overlap detection
Arnd Bergmann <[email protected]>
drm/i915/selftest: fix intel_selftest_modify_policy argument types
Paolo Abeni <[email protected]>
net: fix UaF in netns ops registration error path
Eric Dumazet <[email protected]>
netlink: prevent potential spectre v1 gadgets
Lareine Khawaly <[email protected]>
i2c: designware: use casting of u64 in clock multiplication to avoid overflow
Johan Hovold <[email protected]>
scsi: ufs: core: Fix devfreq deadlocks
Haiyang Zhang <[email protected]>
net: mana: Fix IRQ name - add PCI and queue number
Manivannan Sadhasivam <[email protected]>
EDAC/qcom: Do not pass llcc_driv_data as edac_device_ctl_info's pvt_info
Manivannan Sadhasivam <[email protected]>
EDAC/device: Respect any driver-supplied workqueue polling value
Giulio Benetti <[email protected]>
ARM: 9280/1: mm: fix warning on phys_addr_t to void pointer assignment
Gergely Risko <[email protected]>
ipv6: fix reachability confirmation with proxy_ndp
Srinivas Pandruvada <[email protected]>
thermal: intel: int340x: Protect trip temperature from concurrent updates
Marc Zyngier <[email protected]>
KVM: arm64: GICv4.1: Fix race with doorbell on VPE activation/deactivation
Hendrik Borghorst <[email protected]>
KVM: x86/vmx: Do not skip segment attributes if unusable bit is set
Miklos Szeredi <[email protected]>
ovl: fail on invalid uid/gid mapping at copy up
Namjae Jeon <[email protected]>
ksmbd: limit pdu length size according to connection status
Namjae Jeon <[email protected]>
ksmbd: downgrade ndr version error message to debug
Marios Makassikis <[email protected]>
ksmbd: do not sign response to session request for guest login
Namjae Jeon <[email protected]>
ksmbd: add max connections parameter
Namjae Jeon <[email protected]>
ksmbd: add smbd max io size parameter
Chris Morgan <[email protected]>
i2c: mv64xxx: Add atomic_xfer method to driver
Chris Morgan <[email protected]>
i2c: mv64xxx: Remove shutdown method from driver
David Howells <[email protected]>
cifs: Fix oops due to uncleared server->smbd_conn in reconnect
Steven Rostedt (Google) <[email protected]>
ftrace/scripts: Update the instructions for ftrace-bisect.sh
Natalia Petrova <[email protected]>
trace_events_hist: add check for return value of 'create_hist_field'
Steven Rostedt (Google) <[email protected]>
tracing: Make sure trace_printk() can output as soon as it can be used
Petr Pavlu <[email protected]>
module: Don't wait for GOING modules
Maxim Levitsky <[email protected]>
KVM: SVM: fix tsc scaling cache logic
Alexey V. Vissarionov <[email protected]>
scsi: hpsa: Fix allocation size for scsi_host_alloc()
Harsh Jain <[email protected]>
drm/amdgpu: complete gfxoff allow signal during suspend without delay
Archie Pusaka <[email protected]>
Bluetooth: hci_sync: cancel cmd_timer if hci_open failed
Kees Cook <[email protected]>
exit: Use READ_ONCE() for all oops/warn limit reads
Kees Cook <[email protected]>
docs: Fix path paste-o for /sys/kernel/warn_count
Kees Cook <[email protected]>
panic: Expose "warn_count" to sysfs
Kees Cook <[email protected]>
panic: Introduce warn_limit
Kees Cook <[email protected]>
panic: Consolidate open-coded panic_on_warn checks
Kees Cook <[email protected]>
exit: Allow oops_limit to be disabled
Kees Cook <[email protected]>
exit: Expose "oops_count" to sysfs
Jann Horn <[email protected]>
exit: Put an upper limit on how often we can oops
Kees Cook <[email protected]>
panic: Separate sysctl logic from CONFIG_SMP
Randy Dunlap <[email protected]>
ia64: make IA64_MCA_RECOVERY bool instead of tristate
Nathan Chancellor <[email protected]>
csky: Fix function name in csky_alignment() and die()
Nathan Chancellor <[email protected]>
h8300: Fix build errors from do_exit() to make_task_dead() transition
Nathan Chancellor <[email protected]>
hexagon: Fix function name in die()
Eric W. Biederman <[email protected]>
objtool: Add a missing comma to avoid string concatenation
Eric W. Biederman <[email protected]>
exit: Add and use make_task_dead.
Tiezhu Yang <[email protected]>
kasan: no need to unset panic_on_warn in end_report()
Tiezhu Yang <[email protected]>
ubsan: no need to unset panic_on_warn in ubsan_epilogue()
Tiezhu Yang <[email protected]>
panic: unset panic_on_warn inside panic()
tangmeng <[email protected]>
kernel/panic: move panic sysctls to its own file
Xiaoming Ni <[email protected]>
sysctl: add a new register_sysctl_init() interface
Dongliang Mu <[email protected]>
fs: reiserfs: remove useless new_opts in reiserfs_remount
Deepak Sharma <[email protected]>
x86: ACPI: cstate: Optimize C3 entry on AMD CPUs
Nirmoy Das <[email protected]>
drm/i915: Remove unused variable
Sasha Levin <[email protected]>
Revert "selftests/bpf: check null propagation only neither reg is PTR_TO_BTF_ID"
Thomas Zimmermann <[email protected]>
drm/i915: Allow switching away via vga-switcheroo if uninitialized
Kees Cook <[email protected]>
firmware: coreboot: Check size of table entry and use flex-array
Mateusz Guzik <[email protected]>
lockref: stop doing cpu_relax in the cmpxchg loop
Hans de Goede <[email protected]>
platform/x86: asus-nb-wmi: Add alternate mapping for KEY_SCREENLOCK
Michael Klein <[email protected]>
platform/x86: touchscreen_dmi: Add info for the CSL Panther Tab HD
Andre Przywara <[email protected]>
r8152: add vendor/device ID pair for Microsoft Devkit
Yihang Li <[email protected]>
scsi: hisi_sas: Set a port invalid only if there are no devices attached when refreshing port id
Heiko Carstens <[email protected]>
KVM: s390: interrupt: use READ_ONCE() before cmpxchg()
Bartosz Golaszewski <[email protected]>
spi: spidev: remove debug messages that access spidev->spi without locking
Mark Brown <[email protected]>
ASoC: fsl-asoc-card: Fix naming of AC'97 CODEC widgets
Mark Brown <[email protected]>
ASoC: fsl_ssi: Rename AC'97 streams to avoid collisions with AC'97 CODEC
Miles Chen <[email protected]>
cpufreq: armada-37xx: stop using 0 as NULL pointer
Kan Liang <[email protected]>
perf/x86/intel/uncore: Add Emerald Rapids
Kan Liang <[email protected]>
perf/x86/msr: Add Emerald Rapids
Alexander Gordeev <[email protected]>
s390: expicitly align _edata and _end symbols on page boundary
Niklas Schnelle <[email protected]>
s390/debug: add _ASM_S390_ prefix to header guard
Patrick Thompson <[email protected]>
drm: Add orientation quirk for Lenovo ideapad D330-10IGL
Hui Wang <[email protected]>
net: usb: cdc_ether: add support for Thales Cinterion PLS62-W modem
Chancel Liu <[email protected]>
ASoC: fsl_micfil: Correct the number of steps on SX controls
Konrad Dybcio <[email protected]>
cpufreq: Add SM6375 to cpufreq-dt-platdev blocklist
Max Filippov <[email protected]>
kcsan: test: don't put the expect array on the stack
Sumit Gupta <[email protected]>
cpufreq: Add Tegra234 to cpufreq-dt-platdev blocklist
Wenchao Hao <[email protected]>
scsi: iscsi: Fix multiple iSCSI session unbind events sent to userspace
David Morley <[email protected]>
tcp: fix rate_app_limited to default to 1
Andrew Halaney <[email protected]>
net: stmmac: enable all safety features by default
Viresh Kumar <[email protected]>
thermal: core: call put_device() only after device_register() fails
Dan Carpenter <[email protected]>
thermal/core: fix error code in __thermal_cooling_device_register()
Viresh Kumar <[email protected]>
thermal: Validate new state in cur_state_store()
Daniel Lezcano <[email protected]>
thermal/core: Rename 'trips' to 'num_trips'
Daniel Lezcano <[email protected]>
thermal/core: Remove duplicate information when an error occurs
Rakesh Sankaranarayanan <[email protected]>
net: dsa: microchip: ksz9477: port map correction in ALU table entry register
Willem de Bruijn <[email protected]>
selftests/net: toeplitz: fix race on tpacket_v3 block close
Chen Zhongjin <[email protected]>
driver core: Fix test_async_probe_init saves device in wrong array
Yang Yingliang <[email protected]>
w1: fix WARNING after calling w1_process()
Yang Yingliang <[email protected]>
w1: fix deadloop in __w1_remove_master_device()
Yang Yingliang <[email protected]>
device property: fix of node refcount leak in fwnode_graph_get_next_endpoint()
Eric Pilmore <[email protected]>
ptdma: pt_core_execute_cmd() should use spinlock
Kevin Hao <[email protected]>
octeontx2-pf: Fix the use of GFP_KERNEL in atomic context on rt
Jason Xing <[email protected]>
tcp: avoid the lookup process failing to get sk in ehash table
Keith Busch <[email protected]>
nvme-pci: fix timeout request state check
Hamza Mahfooz <[email protected]>
drm/amd/display: fix issues with driver unload
Geert Uytterhoeven <[email protected]>
phy: phy-can-transceiver: Skip warning if no "max-bitrate"
Liu Shixin <[email protected]>
dmaengine: xilinx_dma: call of_node_put() when breaking out of for_each_child_of_node()
Paulo Alcantara <[email protected]>
cifs: fix potential deadlock in cache_refresh_path()
Pietro Borrello <[email protected]>
HID: betop: check shape of output reports
Eric Dumazet <[email protected]>
l2tp: prevent lockdep issue in l2tp_tunnel_register()
Jason Wang <[email protected]>
virtio-net: correctly enable callback during start_xmit
Robert Hancock <[email protected]>
net: macb: fix PTP TX timestamp failure due to packet padding
Koba Ko <[email protected]>
dmaengine: Fix double increment of client_count in dma_chan_get()
Arnd Bergmann <[email protected]>
drm/panfrost: fix GENERIC_ATOMIC64 dependency
Randy Dunlap <[email protected]>
net: mlx5: eliminate anonymous module_init & module_exit
Maor Dickman <[email protected]>
net/mlx5: E-switch, Fix setting of reserved fields on MODIFY_SCHEDULING_ELEMENT
Caleb Connolly <[email protected]>
net: ipa: disable ipa interrupt during suspend
Ying Hsu <[email protected]>
Bluetooth: Fix possible deadlock in rfcomm_sk_state_change
Udipto Goswami <[email protected]>
usb: gadget: f_fs: Ensure ep0req is dequeued before free_request
Udipto Goswami <[email protected]>
usb: gadget: f_fs: Prevent race during ffs_ep0_queue_wait
Jiri Kosina <[email protected]>
HID: revert CHERRY_MOUSE_000C quirk
Jonas Karlman <[email protected]>
pinctrl: rockchip: fix mux route data for rk3568
Heiner Kallweit <[email protected]>
net: stmmac: fix invalid call to mdiobus_get_phy()
Pietro Borrello <[email protected]>
HID: check empty report_list in bigben_probe()
Pietro Borrello <[email protected]>
HID: check empty report_list in hid_validate_values()
Heiner Kallweit <[email protected]>
net: mdio: validate parameter addr in mdiobus_get_phy()
Szymon Heidrich <[email protected]>
net: usb: sr9700: Handle negative len
Geetha sowjanya <[email protected]>
octeontx2-pf: Avoid use of GFP_KERNEL in atomic context
Cong Wang <[email protected]>
l2tp: close all race conditions in l2tp_tunnel_register()
Cong Wang <[email protected]>
l2tp: convert l2tp_tunnel_list to idr
Jakub Sitnicki <[email protected]>
l2tp: Don't sleep and disable BH under writer-side sk_callback_lock
Jakub Sitnicki <[email protected]>
l2tp: Serialize access to sk_user_data with sk_callback_lock
Eric Dumazet <[email protected]>
net/sched: sch_taprio: fix possible use-after-free
Kurt Kanzenbach <[email protected]>
net: stmmac: Fix queue statistics reading
Jonas Karlman <[email protected]>
pinctrl: rockchip: fix reading pull type on rk3568
Sebastian Reichel <[email protected]>
pinctrl/rockchip: add error handling for pull/drive register getters
Andy Shevchenko <[email protected]>
pinctrl/rockchip: Use temporary variable for struct device
Szymon Heidrich <[email protected]>
wifi: rndis_wlan: Prevent buffer overflow in rndis_query_oid
Marek Vasut <[email protected]>
gpio: mxc: Always set GPIOs used as interrupt source to INPUT mode
Marek Vasut <[email protected]>
gpio: mxc: Protect GPIO irqchip RMW with bgpio spinlock
Schspa Shi <[email protected]>
gpio: use raw spinlock for gpio chip shadowed data
Rahul Rameshbabu <[email protected]>
sch_htb: Avoid grafting on htb_destroy_class_offload when destroying htb
Vladimir Oltean <[email protected]>
net: enetc: avoid deadlock in enetc_tx_onestep_tstamp()
Esina Ekaterina <[email protected]>
net: wan: Add checks for NULL for utdm in undo_uhdlc_init and unmap_si_regs
Jisoo Jang <[email protected]>
net: nfc: Fix use-after-free in local_cleanup()
Shang XiaoJing <[email protected]>
phy: rockchip-inno-usb2: Fix missing clk_disable_unprepare() in rockchip_usb2phy_power_on()
Luis Gerhorst <[email protected]>
bpf: Fix pointer-leak due to insufficient speculative store bypass mitigation
Raju Rangoju <[email protected]>
amd-xgbe: Delay AN timeout during KR training
Raju Rangoju <[email protected]>
amd-xgbe: TX Flow Ctrl Registers are h/w ver dependent
Claudiu Beznea <[email protected]>
ARM: dts: at91: sam9x60: fix the ddr clock for sam9x60
Xingyuan Mo <[email protected]>
NFSD: fix use-after-free in nfsd4_ssc_setup_dul()
Randy Dunlap <[email protected]>
phy: ti: fix Kconfig warning and operator precedence
Konrad Dybcio <[email protected]>
arm64: dts: qcom: msm8992-libra: Fix the memory map
Konrad Dybcio <[email protected]>
arm64: dts: qcom: msm8992-libra: Add CPU regulators
Konrad Dybcio <[email protected]>
arm64: dts: qcom: msm8992: Don't use sfpb mutex
Christophe JAILLET <[email protected]>
PM: AVS: qcom-cpr: Fix an error handling path in cpr_probe()
Alexander Potapenko <[email protected]>
affs: initialize fsdata in affs_truncate()
Dean Luick <[email protected]>
IB/hfi1: Remove user expected buffer invalidate race
Dean Luick <[email protected]>
IB/hfi1: Immediately remove invalid memory from hardware
Dean Luick <[email protected]>
IB/hfi1: Fix expected receive setup error exit issues
Dean Luick <[email protected]>
IB/hfi1: Reserve user expected TIDs
Dean Luick <[email protected]>
IB/hfi1: Reject a zero-length user expected buffer
Yonatan Nachum <[email protected]>
RDMA/core: Fix ib block iterator counter overflow
Masahiro Yamada <[email protected]>
tomoyo: fix broken dependency on *.conf.default
Cristian Marussi <[email protected]>
firmware: arm_scmi: Harden shared memory access in fetch_notification
Cristian Marussi <[email protected]>
firmware: arm_scmi: Harden shared memory access in fetch_response
Miaoqian Lin <[email protected]>
EDAC/highbank: Fix memory leak in highbank_mc_probe()
Hui Tang <[email protected]>
reset: uniphier-glue: Fix possible null-ptr-deref
Philipp Zabel <[email protected]>
reset: uniphier-glue: Use reset_control_bulk API
Miaoqian Lin <[email protected]>
soc: imx8m: Fix incorrect check for of_clk_get_by_name()
Tim Harvey <[email protected]>
arm64: dts: imx8mm-venice-gw7901: fix USB2 controller OC polarity
Jiasheng Jiang <[email protected]>
HID: intel_ish-hid: Add check for ishtp_dma_tx_map
Dario Binacchi <[email protected]>
ARM: imx: add missing of_node_put()
Adam Ford <[email protected]>
arm64: dts: imx8mm-beacon: Fix ecspi2 pinmux
Fabio Estevam <[email protected]>
ARM: dts: imx6qdl-gw560x: Remove incorrect 'uart-has-rtscts'
Fabio Estevam <[email protected]>
ARM: dts: imx7d-pico: Use 'clock-frequency'
Fabio Estevam <[email protected]>
ARM: dts: imx6ul-pico-dwarf: Use 'clock-frequency'
Fabio Estevam <[email protected]>
arm64: dts: imx8mp-phycore-som: Remove invalid PMIC property
Jayesh Choudhary <[email protected]>
dmaengine: ti: k3-udma: Do conditional decrement of UDMA_CHAN_RT_PEER_BCNT_REG
Gaosheng Cui <[email protected]>
memory: mvebu-devbus: Fix missing clk_disable_unprepare in mvebu_devbus_probe()
Gaosheng Cui <[email protected]>
memory: atmel-sdramc: Fix missing clk_disable_unprepare in atmel_ramc_probe()
Ashish Mhetre <[email protected]>
memory: tegra: Remove clients SID override programming
-------------
Diffstat:
Documentation/ABI/testing/sysfs-kernel-oops_count | 6 + Documentation/ABI/testing/sysfs-kernel-warn_count | 6 + Documentation/admin-guide/sysctl/kernel.rst | 19 ++ Makefile | 7 +- arch/alpha/kernel/traps.c | 6 +- arch/alpha/mm/fault.c | 2 +- arch/arm/boot/dts/imx6qdl-gw560x.dtsi | 1 - arch/arm/boot/dts/imx6ul-pico-dwarf.dts | 2 +- arch/arm/boot/dts/imx7d-pico-dwarf.dts | 4 +- arch/arm/boot/dts/imx7d-pico-nymph.dts | 4 +- arch/arm/boot/dts/sam9x60.dtsi | 2 +- arch/arm/kernel/traps.c | 2 +- arch/arm/mach-imx/cpu-imx25.c | 1 + arch/arm/mach-imx/cpu-imx27.c | 1 + arch/arm/mach-imx/cpu-imx31.c | 1 + arch/arm/mach-imx/cpu-imx35.c | 1 + arch/arm/mach-imx/cpu-imx5.c | 1 + arch/arm/mm/fault.c | 2 +- arch/arm/mm/nommu.c | 2 +- .../dts/freescale/imx8mm-beacon-baseboard.dtsi | 4 +- .../boot/dts/freescale/imx8mm-venice-gw7901.dts | 1 + .../boot/dts/freescale/imx8mp-phycore-som.dtsi | 10 - arch/arm64/boot/dts/qcom/msm8992-xiaomi-libra.dts | 90 +++++- arch/arm64/boot/dts/qcom/msm8992.dtsi | 4 - arch/arm64/kernel/traps.c | 2 +- arch/arm64/kvm/vgic/vgic-v3.c | 25 +- arch/arm64/kvm/vgic/vgic-v4.c | 8 +- arch/arm64/kvm/vgic/vgic.h | 1 + arch/arm64/mm/fault.c | 2 +- arch/csky/abiv1/alignment.c | 2 +- arch/csky/kernel/traps.c | 2 +- arch/csky/mm/fault.c | 2 +- arch/h8300/kernel/traps.c | 3 +- arch/h8300/mm/fault.c | 2 +- arch/hexagon/kernel/traps.c | 2 +- arch/ia64/Kconfig | 2 +- arch/ia64/kernel/mca_drv.c | 2 +- arch/ia64/kernel/traps.c | 2 +- arch/ia64/mm/fault.c | 2 +- arch/m68k/kernel/traps.c | 2 +- arch/m68k/mm/fault.c | 2 +- arch/microblaze/kernel/exceptions.c | 4 +- arch/mips/kernel/traps.c | 2 +- arch/nds32/kernel/fpu.c | 2 +- arch/nds32/kernel/traps.c | 8 +- arch/nios2/kernel/traps.c | 4 +- arch/openrisc/kernel/traps.c | 2 +- arch/parisc/kernel/traps.c | 2 +- arch/powerpc/kernel/traps.c | 8 +- arch/riscv/kernel/probes/simulate-insn.c | 4 +- arch/riscv/kernel/traps.c | 2 +- arch/riscv/mm/fault.c | 2 +- arch/s390/include/asm/debug.h | 6 +- arch/s390/kernel/dumpstack.c | 2 +- arch/s390/kernel/nmi.c | 2 +- arch/s390/kernel/vmlinux.lds.S | 2 + arch/s390/kvm/interrupt.c | 12 +- arch/sh/kernel/traps.c | 2 +- arch/sparc/kernel/traps_32.c | 4 +- arch/sparc/kernel/traps_64.c | 4 +- arch/x86/entry/entry_32.S | 6 +- arch/x86/entry/entry_64.S | 6 +- arch/x86/events/amd/core.c | 2 +- arch/x86/events/intel/uncore.c | 1 + arch/x86/events/msr.c | 1 + arch/x86/kernel/acpi/cstate.c | 15 + arch/x86/kernel/dumpstack.c | 4 +- arch/x86/kernel/i8259.c | 1 + arch/x86/kernel/irqinit.c | 4 +- arch/x86/kvm/svm/svm.c | 34 ++- arch/x86/kvm/svm/svm.h | 1 + arch/x86/kvm/vmx/vmx.c | 21 +- arch/xtensa/kernel/traps.c | 2 +- block/blk-core.c | 8 +- drivers/base/property.c | 18 +- drivers/base/test/test_async_driver_probe.c | 2 +- drivers/cpufreq/armada-37xx-cpufreq.c | 2 +- drivers/cpufreq/cpufreq-dt-platdev.c | 2 + drivers/cpufreq/cpufreq_governor.c | 20 +- drivers/cpufreq/cpufreq_governor.h | 1 + drivers/cpufreq/cpufreq_governor_attr_set.c | 5 - drivers/dma/dmaengine.c | 7 +- drivers/dma/ptdma/ptdma-dev.c | 7 +- drivers/dma/ptdma/ptdma.h | 2 +- drivers/dma/ti/k3-udma.c | 5 +- drivers/dma/xilinx/xilinx_dma.c | 4 +- drivers/edac/edac_device.c | 15 +- drivers/edac/highbank_mc_edac.c | 7 +- drivers/edac/qcom_edac.c | 5 +- drivers/firmware/arm_scmi/shmem.c | 9 +- drivers/firmware/google/coreboot_table.c | 9 +- drivers/firmware/google/coreboot_table.h | 1 + drivers/gpio/gpio-amdpt.c | 10 +- drivers/gpio/gpio-brcmstb.c | 12 +- drivers/gpio/gpio-cadence.c | 12 +- drivers/gpio/gpio-dwapb.c | 36 +-- drivers/gpio/gpio-grgpio.c | 30 +- drivers/gpio/gpio-hlwd.c | 18 +- drivers/gpio/gpio-idt3243x.c | 12 +- drivers/gpio/gpio-ixp4xx.c | 4 +- drivers/gpio/gpio-loongson1.c | 8 +- drivers/gpio/gpio-menz127.c | 8 +- drivers/gpio/gpio-mlxbf2.c | 6 +- drivers/gpio/gpio-mmio.c | 22 +- drivers/gpio/gpio-mxc.c | 16 +- drivers/gpio/gpio-sifive.c | 12 +- drivers/gpio/gpio-tb10x.c | 4 +- drivers/gpu/drm/amd/amdgpu/amdgpu_gfx.c | 10 +- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 4 - .../amd/display/amdgpu_dm/amdgpu_dm_mst_types.c | 1 - drivers/gpu/drm/drm_panel_orientation_quirks.c | 6 + drivers/gpu/drm/i915/i915_drv.c | 5 +- drivers/gpu/drm/i915/i915_switcheroo.c | 6 +- .../drm/i915/selftests/intel_scheduler_helpers.c | 3 +- drivers/gpu/drm/panfrost/Kconfig | 3 +- drivers/gpu/drm/vmwgfx/vmwgfx_msg_arm64.h | 0 drivers/hid/hid-betopff.c | 17 +- drivers/hid/hid-bigbenff.c | 5 + drivers/hid/hid-core.c | 4 +- drivers/hid/hid-ids.h | 1 - drivers/hid/hid-quirks.c | 1 - drivers/hid/intel-ish-hid/ishtp/dma-if.c | 10 + drivers/i2c/busses/i2c-designware-common.c | 9 +- drivers/i2c/busses/i2c-mv64xxx.c | 61 +++- drivers/infiniband/core/verbs.c | 7 +- drivers/infiniband/hw/hfi1/user_exp_rcv.c | 200 +++++++++---- drivers/infiniband/hw/hfi1/user_exp_rcv.h | 3 + drivers/input/mouse/synaptics.c | 1 - drivers/memory/atmel-sdramc.c | 6 +- drivers/memory/mvebu-devbus.c | 3 +- drivers/memory/tegra/tegra186.c | 36 --- drivers/net/dsa/microchip/ksz9477.c | 4 +- drivers/net/ethernet/amd/xgbe/xgbe-dev.c | 23 +- drivers/net/ethernet/amd/xgbe/xgbe-mdio.c | 24 ++ drivers/net/ethernet/amd/xgbe/xgbe.h | 2 + drivers/net/ethernet/broadcom/tg3.c | 8 +- drivers/net/ethernet/cadence/macb_main.c | 9 +- drivers/net/ethernet/freescale/enetc/enetc.c | 4 +- .../ethernet/marvell/octeontx2/nic/otx2_common.c | 11 +- .../ethernet/marvell/octeontx2/nic/otx2_common.h | 2 + drivers/net/ethernet/mellanox/mlx5/core/esw/qos.c | 18 +- drivers/net/ethernet/mellanox/mlx5/core/main.c | 8 +- drivers/net/ethernet/microsoft/mana/gdma.h | 3 + drivers/net/ethernet/microsoft/mana/gdma_main.c | 9 +- drivers/net/ethernet/renesas/ravb.h | 4 +- drivers/net/ethernet/renesas/ravb_main.c | 36 ++- drivers/net/ethernet/stmicro/stmmac/dwmac5.c | 14 + .../net/ethernet/stmicro/stmmac/stmmac_ethtool.c | 8 +- drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 5 + drivers/net/ipa/ipa_interrupt.c | 10 + drivers/net/ipa/ipa_interrupt.h | 16 + drivers/net/ipa/ipa_power.c | 17 ++ drivers/net/mdio/mdio-mux-meson-g12a.c | 23 +- drivers/net/phy/mdio_bus.c | 7 +- drivers/net/usb/cdc_ether.c | 6 + drivers/net/usb/r8152.c | 1 + drivers/net/usb/sr9700.c | 2 +- drivers/net/virtio_net.c | 6 +- drivers/net/wan/fsl_ucc_hdlc.c | 6 +- drivers/net/wireless/rndis_wlan.c | 19 +- drivers/nvme/host/core.c | 2 +- drivers/nvme/host/pci.c | 2 +- drivers/phy/phy-can-transceiver.c | 5 +- drivers/phy/rockchip/phy-rockchip-inno-usb2.c | 4 +- drivers/phy/ti/Kconfig | 4 +- drivers/pinctrl/nuvoton/pinctrl-npcm7xx.c | 8 +- drivers/pinctrl/pinctrl-rockchip.c | 315 ++++++++++--------- drivers/pinctrl/pinctrl-rockchip.h | 4 +- drivers/platform/x86/asus-nb-wmi.c | 1 + drivers/platform/x86/touchscreen_dmi.c | 25 ++ drivers/reset/reset-uniphier-glue.c | 37 +-- drivers/scsi/hisi_sas/hisi_sas_main.c | 2 +- drivers/scsi/hpsa.c | 2 +- drivers/scsi/scsi_transport_iscsi.c | 50 +++- drivers/scsi/ufs/ufshcd.c | 26 +- drivers/scsi/ufs/ufshcd.h | 2 + drivers/soc/imx/soc-imx8m.c | 4 +- drivers/soc/qcom/cpr.c | 6 +- drivers/spi/spidev.c | 2 - drivers/thermal/gov_fair_share.c | 10 +- drivers/thermal/gov_power_allocator.c | 4 +- .../intel/int340x_thermal/int340x_thermal_zone.c | 28 +- .../intel/int340x_thermal/int340x_thermal_zone.h | 1 + drivers/thermal/tegra/tegra30-tsensor.c | 2 +- drivers/thermal/thermal_core.c | 53 ++-- drivers/thermal/thermal_helpers.c | 4 +- drivers/thermal/thermal_netlink.c | 2 +- drivers/thermal/thermal_sysfs.c | 33 +- drivers/usb/gadget/function/f_fs.c | 7 + drivers/w1/w1.c | 6 +- drivers/w1/w1_int.c | 5 +- fs/affs/file.c | 2 +- fs/cifs/dfs_cache.c | 42 +-- fs/cifs/smbdirect.c | 1 + fs/ksmbd/connection.c | 17 +- fs/ksmbd/ksmbd_netlink.h | 4 +- fs/ksmbd/ndr.c | 8 +- fs/ksmbd/server.h | 1 + fs/ksmbd/smb2pdu.c | 2 + fs/ksmbd/smb2pdu.h | 5 +- fs/ksmbd/transport_ipc.c | 6 + fs/ksmbd/transport_rdma.c | 8 +- fs/ksmbd/transport_rdma.h | 6 + fs/ksmbd/transport_tcp.c | 17 +- fs/nfsd/nfs4proc.c | 1 + fs/overlayfs/copy_up.c | 4 + fs/proc/proc_sysctl.c | 33 ++ fs/reiserfs/super.c | 6 - include/linux/cpufreq.h | 5 + include/linux/gpio/driver.h | 2 +- include/linux/panic.h | 7 +- include/linux/sched/task.h | 1 + include/linux/sysctl.h | 3 + include/linux/thermal.h | 5 +- include/net/sch_generic.h | 7 + include/net/sock.h | 2 +- include/scsi/scsi_transport_iscsi.h | 9 + include/uapi/linux/netfilter/nf_conntrack_sctp.h | 2 +- include/uapi/linux/netfilter/nfnetlink_cttimeout.h | 2 +- kernel/bpf/verifier.c | 4 +- kernel/exit.c | 72 +++++ kernel/kcsan/kcsan_test.c | 7 +- kernel/kcsan/report.c | 3 +- kernel/module.c | 26 +- kernel/panic.c | 90 +++++- kernel/sched/core.c | 3 +- kernel/sysctl.c | 11 - kernel/trace/trace.c | 2 + kernel/trace/trace.h | 1 + kernel/trace/trace_events_hist.c | 2 + kernel/trace/trace_output.c | 3 +- lib/lockref.c | 1 - lib/nlattr.c | 3 + lib/ubsan.c | 11 +- mm/kasan/report.c | 12 +- mm/kfence/report.c | 3 +- net/bluetooth/hci_core.c | 1 + net/bluetooth/rfcomm/sock.c | 7 +- net/core/net_namespace.c | 2 +- net/ipv4/fib_semantics.c | 2 + net/ipv4/inet_hashtables.c | 17 +- net/ipv4/inet_timewait_sock.c | 8 +- net/ipv4/metrics.c | 2 + net/ipv4/tcp.c | 2 + net/ipv6/ip6_output.c | 15 +- net/l2tp/l2tp_core.c | 116 +++---- net/mctp/af_mctp.c | 1 + net/mctp/route.c | 6 + net/netfilter/nf_conntrack_proto_sctp.c | 122 ++++---- net/netfilter/nf_conntrack_standalone.c | 8 - net/netfilter/nft_set_rbtree.c | 332 +++++++++++++-------- net/netlink/af_netlink.c | 38 ++- net/netrom/nr_timer.c | 1 + net/nfc/llcp_core.c | 1 + net/sched/sch_htb.c | 27 +- net/sched/sch_taprio.c | 2 + net/sctp/bind_addr.c | 6 + scripts/Makefile | 4 +- scripts/dtc/Makefile | 6 +- scripts/kconfig/gconf-cfg.sh | 12 +- scripts/kconfig/mconf-cfg.sh | 16 +- scripts/kconfig/nconf-cfg.sh | 16 +- scripts/kconfig/qconf-cfg.sh | 14 +- scripts/tracing/ftrace-bisect.sh | 34 ++- security/tomoyo/Makefile | 2 +- sound/soc/fsl/fsl-asoc-card.c | 8 +- sound/soc/fsl/fsl_micfil.c | 16 +- sound/soc/fsl/fsl_ssi.c | 4 +- tools/gpio/gpio-event-mon.c | 1 + tools/objtool/Makefile | 4 +- tools/objtool/check.c | 3 +- .../selftests/bpf/prog_tests/jeq_infer_not_null.c | 9 - .../selftests/bpf/progs/jeq_infer_not_null_fail.c | 42 --- tools/testing/selftests/net/toeplitz.c | 12 +- 274 files changed, 2175 insertions(+), 1322 deletions(-)
Greg Kroah-Hartman
maintainerPATCH 1/204 memory: tegra: Remove clients SID override programming
From: Ashish Mhetre <[email protected]>
[ Upstream commit ef86b2c2807f41c045e5534d8513a8b83f63bc39 ]
On newer Tegra releases, early boot SID override programming and SID override programming during resume is handled by bootloader. In the function tegra186_mc_program_sid() which is getting removed, SID override register of all clients is written without checking if secure firmware has allowed write on it or not. If write is disabled by secure firmware then it can lead to errors coming from secure firmware and hang in kernel boot.
Also, SID override is programmed on-demand during probe_finalize() call of IOMMU which is done in tegra186_mc_client_sid_override() in this same file. This function does it correctly by checking if write is permitted on SID override register. It also checks if SID override register is already written with correct value and skips re-writing it in that case.
--- drivers/memory/tegra/tegra186.c | 36 --------------------------------- 1 file changed, 36 deletions(-)
drivers/memory/tegra/tegra186.c +0 -36
@@ -20,32 +20,6 @@#define MC_SID_STREAMID_SECURITY_WRITE_ACCESS_DISABLED BIT(16)#define MC_SID_STREAMID_SECURITY_OVERRIDE BIT(8) -static void tegra186_mc_program_sid (struct tegra_mc *mc) -{ -unsigned int i; - -for (i =0 ; i < mc->soc->num_clients; i++) { -const struct tegra_mc_client *client = &mc->soc->clients[i]; -u32 override, security; - - override =readl (mc->regs + client->regs.sid.override); - security =readl (mc->regs + client->regs.sid.security); - -dev_dbg (mc->dev,"client %s: override: %x security: %x\n" , - client->name, override, security); - -dev_dbg (mc->dev,"setting SID %u for %s\n" , client->sid, - client->name); -writel (client->sid, mc->regs + client->regs.sid.override); - - override =readl (mc->regs + client->regs.sid.override); - security =readl (mc->regs + client->regs.sid.security); - -dev_dbg (mc->dev,"client %s: override: %x security: %x\n" , - client->name, override, security); - } -} -static int tegra186_mc_probe (struct tegra_mc *mc) {int err;
@@ -54,8 +28,6 @@ static int tegra186_mc_probe(struct tegra_mc *mc)if (err <0 )return err; -tegra186_mc_program_sid (mc); -return 0 ; }
@@ -64,13 +36,6 @@ static void tegra186_mc_remove(struct tegra_mc *mc)of_platform_depopulate (mc->dev); } -static int tegra186_mc_resume (struct tegra_mc *mc) -{ -tegra186_mc_program_sid (mc); - -return 0 ; -} -#if IS_ENABLED (CONFIG_IOMMU_API ) static void tegra186_mc_client_sid_override(struct tegra_mc *mc, const struct tegra_mc_client *client,
@@ -142,7 +107,6 @@ static int tegra186_mc_probe_device(struct tegra_mc *mc, struct device *dev)const struct tegra_mc_ops tegra186_mc_ops = { .probe = tegra186_mc_probe, .remove = tegra186_mc_remove, - .resume = tegra186_mc_resume, .probe_device = tegra186_mc_probe_device, };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 2/204 memory: atmel-sdramc: Fix missing clk_disable_unprepare in atmel_ramc_probe()
In reply to Greg Kroah-HartmanFrom: Gaosheng Cui <[email protected]>
[ Upstream commit 340cb392a038cf70540a4cdf2e98a247c66b6df4 ]
The clk_disable_unprepare() should be called in the error handling of caps->has_mpddr_clk, fix it by replacing devm_clk_get and clk_prepare_enable by devm_clk_get_enabled.
--- drivers/memory/atmel-sdramc.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-)
drivers/memory/atmel-sdramc.c +2 -4
@@ -47,19 +47,17 @@ static int atmel_ramc_probe(struct platform_device *pdev) caps =of_device_get_match_data (&pdev->dev);if (caps->has_ddrck) { - clk =devm_clk_get (&pdev->dev,"ddrck" ); + clk =devm_clk_get_enabled (&pdev->dev,"ddrck" );if (IS_ERR (clk))return PTR_ERR (clk); -clk_prepare_enable (clk); }if (caps->has_mpddr_clk) { - clk =devm_clk_get (&pdev->dev,"mpddr" ); + clk =devm_clk_get_enabled (&pdev->dev,"mpddr" );if (IS_ERR (clk)) {pr_err ("AT91 RAMC: couldn't get mpddr clock\n" );return PTR_ERR (clk); } -clk_prepare_enable (clk); }return 0 ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 3/204 memory: mvebu-devbus: Fix missing clk_disable_unprepare in mvebu_devbus_probe()
In reply to Greg Kroah-HartmanFrom: Gaosheng Cui <[email protected]>
[ Upstream commit cb8fd6f75775165390ededea8799b60d93d9fe3e ]
The clk_disable_unprepare() should be called in the error handling of devbus_get_timing_params() and of_platform_populate(), fix it by replacing devm_clk_get and clk_prepare_enable by devm_clk_get_enabled.
--- drivers/memory/mvebu-devbus.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
drivers/memory/mvebu-devbus.c +1 -2
@@ -280,10 +280,9 @@ static int mvebu_devbus_probe(struct platform_device *pdev)if (IS_ERR (devbus->base))return PTR_ERR (devbus->base); - clk =devm_clk_get (&pdev->dev,NULL ); + clk =devm_clk_get_enabled (&pdev->dev,NULL );if (IS_ERR (clk))return PTR_ERR (clk); -clk_prepare_enable (clk);/* * Obtain clock period in picoseconds,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 4/204 dmaengine: ti: k3-udma: Do conditional decrement of UDMA_CHAN_RT_PEER_BCNT_REG
In reply to Greg Kroah-HartmanFrom: Jayesh Choudhary <[email protected]>
[ Upstream commit efab25894a41a920d9581183741e7fadba00719c ]
PSIL_EP_NATIVE endpoints may not have PEER registers for BCNT and thus udma_decrement_byte_counters() should not try to decrement these counters. This fixes the issue of crypto IPERF testing where the client side (EVM) hangs without transfer of packets to the server side, seen since this function was added.
--- drivers/dma/ti/k3-udma.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
drivers/dma/ti/k3-udma.c +3 -2
@@ -760,11 +760,12 @@ static void udma_decrement_byte_counters(struct udma_chan *uc, u32 val)if (uc->desc->dir ==DMA_DEV_TO_MEM ) {udma_rchanrt_write (uc,UDMA_CHAN_RT_BCNT_REG , val);udma_rchanrt_write (uc,UDMA_CHAN_RT_SBCNT_REG , val); -udma_rchanrt_write (uc,UDMA_CHAN_RT_PEER_BCNT_REG , val); +if (uc->config.ep_type !=PSIL_EP_NATIVE ) +udma_rchanrt_write (uc,UDMA_CHAN_RT_PEER_BCNT_REG , val); }else {udma_tchanrt_write (uc,UDMA_CHAN_RT_BCNT_REG , val);udma_tchanrt_write (uc,UDMA_CHAN_RT_SBCNT_REG , val); -if (!uc->bchan) +if (!uc->bchan && uc->config.ep_type !=PSIL_EP_NATIVE )udma_tchanrt_write (uc,UDMA_CHAN_RT_PEER_BCNT_REG , val); } }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 5/204 arm64: dts: imx8mp-phycore-som: Remove invalid PMIC property
In reply to Greg Kroah-HartmanFrom: Fabio Estevam <[email protected]>
[ Upstream commit cfd04dd1c4b6c33afc2a934b957d71cf8ddd1539 ]
'regulator-compatible' is not a valid property according to nxp,pca9450-regulator.yaml and causes the following warning:
DTC_CHK arch/arm64/boot/dts/freescale/imx8mp-dhcom-pdk2.dtb
...
pmic@25: regulators:LDO1: Unevaluated properties are not allowed ('regulator-compatible' was unexpected)
Remove the invalid 'regulator-compatible' property.
--- arch/arm64/boot/dts/freescale/imx8mp-phycore-som.dtsi | 10 ---------- 1 file changed, 10 deletions(-)
arch/arm64/boot/dts/freescale/imx8mp-phycore-som.dtsi +0 -10
@@ -98,7 +98,6 @@ pmic: pmic@25 { regulators { buck1: BUCK1 { - regulator-compatible = "BUCK1"; regulator-min-microvolt = <600000>; regulator-max-microvolt = <2187500>; regulator-boot-on;
@@ -107,7 +106,6 @@ buck1: BUCK1 { }; buck2: BUCK2 { - regulator-compatible = "BUCK2"; regulator-min-microvolt = <600000>; regulator-max-microvolt = <2187500>; regulator-boot-on;
@@ -116,7 +114,6 @@ buck2: BUCK2 { }; buck4: BUCK4 { - regulator-compatible = "BUCK4"; regulator-min-microvolt = <600000>; regulator-max-microvolt = <3400000>; regulator-boot-on;
@@ -124,7 +121,6 @@ buck4: BUCK4 { }; buck5: BUCK5 { - regulator-compatible = "BUCK5"; regulator-min-microvolt = <600000>; regulator-max-microvolt = <3400000>; regulator-boot-on;
@@ -132,7 +128,6 @@ buck5: BUCK5 { }; buck6: BUCK6 { - regulator-compatible = "BUCK6"; regulator-min-microvolt = <600000>; regulator-max-microvolt = <3400000>; regulator-boot-on;
@@ -140,7 +135,6 @@ buck6: BUCK6 { }; ldo1: LDO1 { - regulator-compatible = "LDO1"; regulator-min-microvolt = <1600000>; regulator-max-microvolt = <3300000>; regulator-boot-on;
@@ -148,7 +142,6 @@ ldo1: LDO1 { }; ldo2: LDO2 { - regulator-compatible = "LDO2"; regulator-min-microvolt = <800000>; regulator-max-microvolt = <1150000>; regulator-boot-on;
@@ -156,7 +149,6 @@ ldo2: LDO2 { }; ldo3: LDO3 { - regulator-compatible = "LDO3"; regulator-min-microvolt = <800000>; regulator-max-microvolt = <3300000>; regulator-boot-on;
@@ -164,7 +156,6 @@ ldo3: LDO3 { }; ldo4: LDO4 { - regulator-compatible = "LDO4"; regulator-min-microvolt = <800000>; regulator-max-microvolt = <3300000>; regulator-boot-on;
@@ -172,7 +163,6 @@ ldo4: LDO4 { }; ldo5: LDO5 { - regulator-compatible = "LDO5"; regulator-min-microvolt = <1800000>; regulator-max-microvolt = <3300000>; };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 6/204 ARM: dts: imx6ul-pico-dwarf: Use clock-frequency
In reply to Greg Kroah-HartmanFrom: Fabio Estevam <[email protected]>
[ Upstream commit 94e2cf1e0db5b06c7a6ae0878c5cbec925819a8a ]
'clock_frequency' is not a valid property.
Use the correct 'clock-frequency' instead.
--- arch/arm/boot/dts/imx6ul-pico-dwarf.dts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/arm/boot/dts/imx6ul-pico-dwarf.dts +1 -1
@@ -32,7 +32,7 @@ sys_mclk: clock-sys-mclk { }; &i2c2 { - clock_frequency = <100000>; + clock-frequency = <100000>; pinctrl-names = "default"; pinctrl-0 = <&pinctrl_i2c2>; status = "okay";
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 7/204 ARM: dts: imx7d-pico: Use clock-frequency
In reply to Greg Kroah-HartmanFrom: Fabio Estevam <[email protected]>
[ Upstream commit f4dd0845c4f1f5371f1e06fef0e4a1734a2db964 ]
'clock_frequency' is not a valid property.
Use the correct 'clock-frequency' instead.
--- arch/arm/boot/dts/imx7d-pico-dwarf.dts | 4 ++-- arch/arm/boot/dts/imx7d-pico-nymph.dts | 4 ++-- 2 files changed, 4 insertions(+), 4 deletions(-)
arch/arm/boot/dts/imx7d-pico-dwarf.dts +2 -2
@@ -32,7 +32,7 @@ sys_mclk: clock-sys-mclk { }; &i2c1 { - clock_frequency = <100000>; + clock-frequency = <100000>; pinctrl-names = "default"; pinctrl-0 = <&pinctrl_i2c1>; status = "okay";
@@ -52,7 +52,7 @@ pressure-sensor@60 { }; &i2c4 { - clock_frequency = <100000>; + clock-frequency = <100000>; pinctrl-names = "default"; pinctrl-0 = <&pinctrl_i2c1>; status = "okay";
arch/arm/boot/dts/imx7d-pico-nymph.dts +2 -2
@@ -43,7 +43,7 @@ sys_mclk: clock-sys-mclk { }; &i2c1 { - clock_frequency = <100000>; + clock-frequency = <100000>; pinctrl-names = "default"; pinctrl-0 = <&pinctrl_i2c1>; status = "okay";
@@ -64,7 +64,7 @@ adc@52 { }; &i2c2 { - clock_frequency = <100000>; + clock-frequency = <100000>; pinctrl-names = "default"; pinctrl-0 = <&pinctrl_i2c2>; status = "okay";
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 8/204 ARM: dts: imx6qdl-gw560x: Remove incorrect uart-has-rtscts
In reply to Greg Kroah-HartmanFrom: Fabio Estevam <[email protected]>
[ Upstream commit 9dfbc72256b5de608ad10989bcbafdbbd1ac8d4e ]
The following build warning is seen when running:
make dtbs_check DT_SCHEMA_FILES=fsl-imx-uart.yaml
arch/arm/boot/dts/imx6dl-gw560x.dtb: serial@2020000: rts-gpios: False schema does not allow [[20, 1, 0]]
From schema: Documentation/devicetree/bindings/serial/fsl-imx-uart.yaml
The imx6qdl-gw560x board does not expose the UART RTS and CTS as native UART pins, so 'uart-has-rtscts' should not be used.
Using 'uart-has-rtscts' with 'rts-gpios' is an invalid combination detected by serial.yaml.
Fix the problem by removing the incorrect 'uart-has-rtscts' property.
--- arch/arm/boot/dts/imx6qdl-gw560x.dtsi | 1 - 1 file changed, 1 deletion(-)
arch/arm/boot/dts/imx6qdl-gw560x.dtsi +0 -1
@@ -632,7 +632,6 @@ &ssi1 { &uart1 { pinctrl-names = "default"; pinctrl-0 = <&pinctrl_uart1>; - uart-has-rtscts; rts-gpios = <&gpio7 1 GPIO_ACTIVE_HIGH>; status = "okay"; };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 9/204 arm64: dts: imx8mm-beacon: Fix ecspi2 pinmux
In reply to Greg Kroah-HartmanFrom: Adam Ford <[email protected]>
[ Upstream commit 5225ba9db112ec4ed67da5e4d8b72e618573955e ]
Early hardware did not support hardware handshaking on the UART, but final production hardware did. When the hardware was updated the chip select was changed to facilitate hardware handshaking on UART3. Fix the ecspi2 pin mux to eliminate a pin conflict with UART3 and allow the EEPROM to operate again.
--- arch/arm64/boot/dts/freescale/imx8mm-beacon-baseboard.dtsi | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/arm64/boot/dts/freescale/imx8mm-beacon-baseboard.dtsi +2 -2
@@ -70,7 +70,7 @@ sound { &ecspi2 { pinctrl-names = "default"; pinctrl-0 = <&pinctrl_espi2>; - cs-gpios = <&gpio5 9 GPIO_ACTIVE_LOW>; + cs-gpios = <&gpio5 13 GPIO_ACTIVE_LOW>; status = "okay"; eeprom@0 {
@@ -186,7 +186,7 @@ pinctrl_espi2: espi2grp { MX8MM_IOMUXC_ECSPI2_SCLK_ECSPI2_SCLK 0x82 MX8MM_IOMUXC_ECSPI2_MOSI_ECSPI2_MOSI 0x82 MX8MM_IOMUXC_ECSPI2_MISO_ECSPI2_MISO 0x82 - MX8MM_IOMUXC_ECSPI1_SS0_GPIO5_IO9 0x41 + MX8MM_IOMUXC_ECSPI2_SS0_GPIO5_IO13 0x41 >; };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 10/204 ARM: imx: add missing of_node_put()
In reply to Greg Kroah-HartmanFrom: Dario Binacchi <[email protected]>
[ Upstream commit 87b30c4b0efb6a194a7b8eac2568a3da520d905f ]
Calling of_find_compatible_node() returns a node pointer with refcount incremented. Use of_node_put() on it when done.
The patch fixes the same problem on different i.MX platforms.
--- arch/arm/mach-imx/cpu-imx25.c | 1 + arch/arm/mach-imx/cpu-imx27.c | 1 + arch/arm/mach-imx/cpu-imx31.c | 1 + arch/arm/mach-imx/cpu-imx35.c | 1 + arch/arm/mach-imx/cpu-imx5.c | 1 + 5 files changed, 5 insertions(+)
arch/arm/mach-imx/cpu-imx25.c +1 -0
@@ -23,6 +23,7 @@ static int mx25_read_cpu_rev(void) np =of_find_compatible_node (NULL ,NULL ,"fsl,imx25-iim" ); iim_base =of_iomap (np,0 ); +of_node_put (np);BUG_ON (!iim_base); rev =readl (iim_base +MXC_IIMSREV );iounmap (iim_base);
arch/arm/mach-imx/cpu-imx27.c +1 -0
@@ -28,6 +28,7 @@ static int mx27_read_cpu_rev(void) np =of_find_compatible_node (NULL ,NULL ,"fsl,imx27-ccm" ); ccm_base =of_iomap (np,0 ); +of_node_put (np);BUG_ON (!ccm_base);/* * now we have access to the IO registers. As we need
arch/arm/mach-imx/cpu-imx31.c +1 -0
@@ -39,6 +39,7 @@ static int mx31_read_cpu_rev(void) np =of_find_compatible_node (NULL ,NULL ,"fsl,imx31-iim" ); iim_base =of_iomap (np,0 ); +of_node_put (np);BUG_ON (!iim_base);/* read SREV register from IIM module */
arch/arm/mach-imx/cpu-imx35.c +1 -0
@@ -21,6 +21,7 @@ static int mx35_read_cpu_rev(void) np =of_find_compatible_node (NULL ,NULL ,"fsl,imx35-iim" ); iim_base =of_iomap (np,0 ); +of_node_put (np);BUG_ON (!iim_base); rev =imx_readl (iim_base +MXC_IIMSREV );
arch/arm/mach-imx/cpu-imx5.c +1 -0
@@ -28,6 +28,7 @@ static u32 imx5_read_srev_reg(const char *compat) np =of_find_compatible_node (NULL ,NULL , compat); iim_base =of_iomap (np,0 ); +of_node_put (np);WARN_ON (!iim_base); srev =readl (iim_base +IIM_SREV ) &0xff ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 11/204 HID: intel_ish-hid: Add check for ishtp_dma_tx_map
In reply to Greg Kroah-HartmanFrom: Jiasheng Jiang <[email protected]>
[ Upstream commit b3d40c3ec3dc4ad78017de6c3a38979f57aaaab8 ]
As the kcalloc may return NULL pointer,
it should be better to check the ishtp_dma_tx_map before use in order to avoid NULL pointer dereference.
--- drivers/hid/intel-ish-hid/ishtp/dma-if.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
drivers/hid/intel-ish-hid/ishtp/dma-if.c +10 -0
@@ -104,6 +104,11 @@ void *ishtp_cl_get_dma_send_buf(struct ishtp_device *dev,int required_slots = (size /DMA_SLOT_SIZE ) +1 * (size %DMA_SLOT_SIZE !=0 ); +if (!dev->ishtp_dma_tx_map) { +dev_err (dev->devc,"Fail to allocate Tx map\n" ); +return NULL ; + } +spin_lock_irqsave (&dev->ishtp_dma_tx_lock, flags);for (i =0 ; i <= (dev->ishtp_dma_num_slots - required_slots); i++) { free =1 ;
@@ -150,6 +155,11 @@ void ishtp_cl_release_dma_acked_mem(struct ishtp_device *dev,return ; } +if (!dev->ishtp_dma_tx_map) { +dev_err (dev->devc,"Fail to allocate Tx map\n" ); +return ; + } + i = (msg_addr - dev->ishtp_host_dma_tx_buf) /DMA_SLOT_SIZE ;spin_lock_irqsave (&dev->ishtp_dma_tx_lock, flags);for (j =0 ; j < acked_slots; j++) {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 12/204 arm64: dts: imx8mm-venice-gw7901: fix USB2 controller OC polarity
In reply to Greg Kroah-HartmanFrom: Tim Harvey <[email protected]>
[ Upstream commit ae066f374687d7dd06bb8c732f66d6ab3c3fd480 ]
The GW7901 has USB2 routed to a USB VBUS supply with over-current protection via an active-low pin. Define the OC pin polarity properly.
--- arch/arm64/boot/dts/freescale/imx8mm-venice-gw7901.dts | 1 + 1 file changed, 1 insertion(+)
arch/arm64/boot/dts/freescale/imx8mm-venice-gw7901.dts +1 -0
@@ -675,6 +675,7 @@ &usbotg1 { &usbotg2 { dr_mode = "host"; vbus-supply = <®_usb2_vbus>; + over-current-active-low; status = "okay"; };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 13/204 soc: imx8m: Fix incorrect check for of_clk_get_by_name()
In reply to Greg Kroah-HartmanFrom: Miaoqian Lin <[email protected]>
[ Upstream commit 490748874ebf1875420fc29b335bba2075dd1b5e ]
of_clk_get_by_name() returns error pointers instead of NULL. Use IS_ERR() checks the return value to catch errors.
--- drivers/soc/imx/soc-imx8m.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/soc/imx/soc-imx8m.c +2 -2
@@ -66,8 +66,8 @@ static u32 __init imx8mq_soc_revision(void) ocotp_base =of_iomap (np,0 );WARN_ON (!ocotp_base); clk =of_clk_get_by_name (np,NULL ); -if (!clk) { -WARN_ON (!clk); +if (IS_ERR (clk)) { +WARN_ON (IS_ERR (clk));return 0 ; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 14/204 reset: uniphier-glue: Use reset_control_bulk API
In reply to Greg Kroah-HartmanFrom: Philipp Zabel <[email protected]>
[ Upstream commit 176cae38719196a43cd8ae08377413a3884a9f15 ]
This driver already uses the clk_bulk API. Simplify the driver by using the reset_control_bulk API as well.
Stable-dep-of: 3a2390c6777e ("reset: uniphier-glue: Fix possible null-ptr-deref")
--- drivers/reset/reset-uniphier-glue.c | 33 ++++++++++++----------------- 1 file changed, 14 insertions(+), 19 deletions(-)
drivers/reset/reset-uniphier-glue.c +14 -19
@@ -23,7 +23,7 @@ struct uniphier_glue_reset_soc_data {struct uniphier_glue_reset_priv {struct clk_bulk_data clk[MAX_CLKS ]; -struct reset_control *rst[MAX_RSTS ]; +struct reset_control_bulk_data rst[MAX_RSTS ];struct reset_simple_data rdata;const struct uniphier_glue_reset_soc_data *data; };
@@ -34,8 +34,7 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)struct uniphier_glue_reset_priv *priv;struct resource *res;resource_size_t size; -const char *name; -int i, ret, nr; +int i, ret; priv =devm_kzalloc (dev,sizeof (*priv),GFP_KERNEL );if (!priv)
@@ -58,22 +57,20 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)if (ret)return ret; -for (i =0 ; i < priv->data->nrsts; i++) { - name = priv->data->reset_names[i]; - priv->rst[i] =devm_reset_control_get_shared (dev, name); -if (IS_ERR (priv->rst[i])) -return PTR_ERR (priv->rst[i]); - } +for (i =0 ; i < priv->data->nrsts; i++) + priv->rst[i].id = priv->data->reset_names[i]; + ret =devm_reset_control_bulk_get_shared (dev, priv->data->nrsts, + priv->rst); +if (ret) +return ret; ret =clk_bulk_prepare_enable (priv->data->nclks, priv->clk);if (ret)return ret; -for (nr =0 ; nr < priv->data->nrsts; nr++) { - ret =reset_control_deassert (priv->rst[nr]); -if (ret) - goto out_rst_assert; - } + ret =reset_control_bulk_deassert (priv->data->nrsts, priv->rst); +if (ret) + goto out_clk_disable;spin_lock_init (&priv->rdata.lock); priv->rdata.rcdev.owner =THIS_MODULE ;
@@ -91,9 +88,9 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)return 0 ; out_rst_assert: -while (nr--) -reset_control_assert (priv->rst[nr]); +reset_control_bulk_assert (priv->data->nrsts, priv->rst); +out_clk_disable:clk_bulk_disable_unprepare (priv->data->nclks, priv->clk);return ret;
@@ -102,10 +99,8 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)static int uniphier_glue_reset_remove (struct platform_device *pdev) {struct uniphier_glue_reset_priv *priv =platform_get_drvdata (pdev); -int i; -for (i =0 ; i < priv->data->nrsts; i++) -reset_control_assert (priv->rst[i]); +reset_control_bulk_assert (priv->data->nrsts, priv->rst);clk_bulk_disable_unprepare (priv->data->nclks, priv->clk);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 15/204 reset: uniphier-glue: Fix possible null-ptr-deref
In reply to Greg Kroah-HartmanFrom: Hui Tang <[email protected]>
[ Upstream commit 3a2390c6777e3f6662980c6cfc25cafe9e4fef98 ]
It will cause null-ptr-deref when resource_size(res) invoked, if platform_get_resource() returns NULL.
--- drivers/reset/reset-uniphier-glue.c | 4 +--- 1 file changed, 1 insertion(+), 3 deletions(-)
drivers/reset/reset-uniphier-glue.c +1 -3
@@ -33,7 +33,6 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)struct device *dev = &pdev->dev;struct uniphier_glue_reset_priv *priv;struct resource *res; -resource_size_t size;int i, ret; priv =devm_kzalloc (dev,sizeof (*priv),GFP_KERNEL );
@@ -46,7 +45,6 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)return -EINVAL ; res =platform_get_resource (pdev,IORESOURCE_MEM ,0 ); - size =resource_size (res); priv->rdata.membase =devm_ioremap_resource (dev, res);if (IS_ERR (priv->rdata.membase))return PTR_ERR (priv->rdata.membase);
@@ -74,7 +72,7 @@ static int uniphier_glue_reset_probe(struct platform_device *pdev)spin_lock_init (&priv->rdata.lock); priv->rdata.rcdev.owner =THIS_MODULE ; - priv->rdata.rcdev.nr_resets = size *BITS_PER_BYTE ; + priv->rdata.rcdev.nr_resets =resource_size (res) *BITS_PER_BYTE ; priv->rdata.rcdev.ops = &reset_simple_ops; priv->rdata.rcdev.of_node = dev->of_node; priv->rdata.active_low = true;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 16/204 EDAC/highbank: Fix memory leak in highbank_mc_probe()
In reply to Greg Kroah-HartmanFrom: Miaoqian Lin <[email protected]>
[ Upstream commit e7a293658c20a7945014570e1921bf7d25d68a36 ]
When devres_open_group() fails, it returns -ENOMEM without freeing memory allocated by edac_mc_alloc().
Call edac_mc_free() on the error handling path to avoid a memory leak.
[ bp: Massage commit message. ]
--- drivers/edac/highbank_mc_edac.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/edac/highbank_mc_edac.c +5 -2
@@ -174,8 +174,10 @@ static int highbank_mc_probe(struct platform_device *pdev) drvdata = mci->pvt_info;platform_set_drvdata (pdev, mci); -if (!devres_open_group (&pdev->dev,NULL ,GFP_KERNEL )) -return -ENOMEM ; +if (!devres_open_group (&pdev->dev,NULL ,GFP_KERNEL )) { + res = -ENOMEM ; + goto free; + } r =platform_get_resource (pdev,IORESOURCE_MEM ,0 );if (!r) {
@@ -243,6 +245,7 @@ static int highbank_mc_probe(struct platform_device *pdev)edac_mc_del_mc (&pdev->dev); err:devres_release_group (&pdev->dev,NULL ); +free:edac_mc_free (mci);return res; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 17/204 firmware: arm_scmi: Harden shared memory access in fetch_response
In reply to Greg Kroah-HartmanFrom: Cristian Marussi <[email protected]>
[ Upstream commit ad78b81a1077f7d956952cd8bdfe1e61504e3eb8 ]
A misbheaving SCMI platform firmware could reply with out-of-spec messages, shorter than the mimimum size comprising a header and a status field.
Harden shmem_fetch_response to properly truncate such a bad messages.
--- drivers/firmware/arm_scmi/shmem.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
drivers/firmware/arm_scmi/shmem.c +3 -2
@@ -58,10 +58,11 @@ u32 shmem_read_header(struct scmi_shared_mem __iomem *shmem)void shmem_fetch_response (struct scmi_shared_mem __iomem *shmem,struct scmi_xfer *xfer) { +size_t len =ioread32 (&shmem->length); + xfer->hdr.status =ioread32 (shmem->msg_payload);/* Skip the length of header and status in shmem area i.e 8 bytes */ - xfer->rx.len =min_t (size_t, xfer->rx.len, -ioread32 (&shmem->length) -8 ); + xfer->rx.len =min_t (size_t, xfer->rx.len, len >8 ? len -8 :0 );/* Take a copy to the rx buffer.. */ memcpy_fromio (xfer->rx.buf, shmem->msg_payload +4 , xfer->rx.len);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 18/204 firmware: arm_scmi: Harden shared memory access in fetch_notification
In reply to Greg Kroah-HartmanFrom: Cristian Marussi <[email protected]>
[ Upstream commit 9bae076cd4e3e3c3dc185cae829d80b2dddec86e ]
A misbheaving SCMI platform firmware could reply with out-of-spec notifications, shorter than the mimimum size comprising a header.
--- drivers/firmware/arm_scmi/shmem.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/firmware/arm_scmi/shmem.c +3 -1
@@ -71,8 +71,10 @@ void shmem_fetch_response(struct scmi_shared_mem __iomem *shmem,void shmem_fetch_notification (struct scmi_shared_mem __iomem *shmem,size_t max_len,struct scmi_xfer *xfer) { +size_t len =ioread32 (&shmem->length); +/* Skip only the length of header in shmem area i.e 4 bytes */ - xfer->rx.len =min_t (size_t, max_len,ioread32 (&shmem->length) -4 ); + xfer->rx.len =min_t (size_t, max_len, len >4 ? len -4 :0 );/* Take a copy to the rx buffer.. */ memcpy_fromio (xfer->rx.buf, shmem->msg_payload, xfer->rx.len);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 19/204 tomoyo: fix broken dependency on *.conf.default
In reply to Greg Kroah-HartmanFrom: Masahiro Yamada <[email protected]>
[ Upstream commit eaf2213ba563b2d74a1f2c13a6b258273f689802 ]
If *.conf.default is updated, builtin-policy.h should be rebuilt, but this does not work when compiled with O= option.
[Without this commit]
$ touch security/tomoyo/policy/exception_policy.conf.default
$ make O=/tmp security/tomoyo/
make[1]: Entering directory '/tmp'
GEN Makefile
CALL /home/masahiro/ref/linux/scripts/checksyscalls.sh
DESCEND objtool
make[1]: Leaving directory '/tmp'[With this commit]
$ touch security/tomoyo/policy/exception_policy.conf.default
$ make O=/tmp security/tomoyo/
make[1]: Entering directory '/tmp'
GEN Makefile
CALL /home/masahiro/ref/linux/scripts/checksyscalls.sh
DESCEND objtool
POLICY security/tomoyo/builtin-policy.h
CC security/tomoyo/common.o
AR security/tomoyo/built-in.a
make[1]: Leaving directory '/tmp'$(srctree)/ is essential because $(wildcard ) does not follow VPATH.
--- security/tomoyo/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
security/tomoyo/Makefile +1 -1
@@ -10,7 +10,7 @@ endef quiet_cmd_policy = POLICY $@ cmd_policy = ($(call do_policy,profile); $(call do_policy,exception_policy); $(call do_policy,domain_policy); $(call do_policy,manager); $(call do_policy,stat)) >$@ -$(obj)/builtin-policy.h: $(wildcard $(obj)/policy/*.conf $(src)/policy/*.conf.default) FORCE +$(obj)/builtin-policy.h: $(wildcard $(obj)/policy/*.conf $(srctree)/$(src)/policy/*.conf.default) FORCE $(call if_changed,policy) $(obj)/common.o: $(obj)/builtin-policy.h
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 20/204 RDMA/core: Fix ib block iterator counter overflow
In reply to Greg Kroah-HartmanFrom: Yonatan Nachum <[email protected]>
[ Upstream commit 0afec5e9cea732cb47014655685a2a47fb180c31 ]
When registering a new DMA MR after selecting the best aligned page size for it, we iterate over the given sglist to split each entry to smaller, aligned to the selected page size, DMA blocks.
In given circumstances where the sg entry and page size fit certain sizes and the sg entry is not aligned to the selected page size, the total size of the aligned pages we need to cover the sg entry is >= 4GB. Under this circumstances, while iterating page aligned blocks, the counter responsible for counting how much we advanced from the start of the sg entry is overflowed because its type is u32 and we pass 4GB in size. This can lead to an infinite loop inside the iterator function because the overflow prevents the counter to be larger
than the size of the sg entry.
Fix the presented problem by changing the advancement condition to eliminate overflow.
Backtrace: [ 192.374329] efa_reg_user_mr_dmabuf [ 192.376783] efa_register_mr [ 192.382579] pgsz_bitmap 0xfffff000 rounddown 0x80000000 [ 192.386423] pg_sz [0x80000000] umem_length[0xc0000000] [ 192.392657] start 0x0 length 0xc0000000 params.page_shift 31 params.page_num 3 [ 192.399559] hp_cnt[3], pages_in_hp[524288] [ 192.403690] umem->sgt_append.sgt.nents[1] [ 192.407905] number entries: [1], pg_bit: [31] [ 192.411397] biter->__sg_nents [1] biter->__sg [0000000008b0c5d8] [ 192.415601] biter->__sg_advance [665837568] sg_dma_len[3221225472] [ 192.419823] biter->__sg_nents [1] biter->__sg [0000000008b0c5d8] [ 192.423976] biter->__sg_advance [2813321216] sg_dma_len[3221225472] [ 192.428243] biter->__sg_nents [1] biter->__sg [0000000008b0c5d8] [ 192.432397] biter->__sg_advance [665837568] sg_dma_len[3221225472]
--- drivers/infiniband/core/verbs.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/infiniband/core/verbs.c +5 -2
@@ -2965,15 +2965,18 @@ EXPORT_SYMBOL(__rdma_block_iter_start);bool __rdma_block_iter_next (struct ib_block_iter *biter) {unsigned int block_offset; +unsigned int sg_delta;if (!biter->__sg_nents || !biter->__sg)return false; biter->__dma_addr =sg_dma_address (biter->__sg) + biter->__sg_advance; block_offset = biter->__dma_addr & (BIT_ULL (biter->__pg_bit) -1 ); - biter->__sg_advance +=BIT_ULL (biter->__pg_bit) - block_offset; + sg_delta =BIT_ULL (biter->__pg_bit) - block_offset; -if (biter->__sg_advance >=sg_dma_len (biter->__sg)) { +if (sg_dma_len (biter->__sg) - biter->__sg_advance > sg_delta) { + biter->__sg_advance += sg_delta; + }else { biter->__sg_advance =0 ; biter->__sg =sg_next (biter->__sg); biter->__sg_nents--;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 21/204 IB/hfi1: Reject a zero-length user expected buffer
In reply to Greg Kroah-HartmanFrom: Dean Luick <[email protected]>
[ Upstream commit 0a0a6e80472c98947d73c3d13bcd7d101895f55d ]
A zero length user buffer makes no sense and the code does not handle it correctly. Instead, reject a zero length as invalid.
--- drivers/infiniband/hw/hfi1/user_exp_rcv.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/infiniband/hw/hfi1/user_exp_rcv.c +2 -0
@@ -256,6 +256,8 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd,if (!PAGE_ALIGNED (tinfo->vaddr))return -EINVAL ; +if (tinfo->length ==0 ) +return -EINVAL ; tidbuf =kzalloc (sizeof (*tidbuf),GFP_KERNEL );if (!tidbuf)
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 22/204 IB/hfi1: Reserve user expected TIDs
In reply to Greg Kroah-HartmanFrom: Dean Luick <[email protected]>
[ Upstream commit ecf91551cdd2925ed6d9a9d99074fa5f67b90596 ]
To avoid a race, reserve the number of user expected TIDs before setup.
--- drivers/infiniband/hw/hfi1/user_exp_rcv.c | 14 ++++++-------- 1 file changed, 6 insertions(+), 8 deletions(-)
drivers/infiniband/hw/hfi1/user_exp_rcv.c +6 -8
@@ -282,16 +282,13 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd,/* Find sets of physically contiguous pages */ tidbuf->n_psets =find_phys_blocks (tidbuf, pinned); -/* -* We don't need to access this under a lock since tid_used is per -* process and the same process cannot be in hfi1_user_exp_rcv_clear() -* and hfi1_user_exp_rcv_setup() at the same time. -*/ +/* Reserve the number of expected tids to be used. */ spin_lock (&fd->tid_lock);if (fd->tid_used + tidbuf->n_psets > fd->tid_limit) pageset_count = fd->tid_limit - fd->tid_used;else pageset_count = tidbuf->n_psets; + fd->tid_used += pageset_count;spin_unlock (&fd->tid_lock);if (!pageset_count)
@@ -400,10 +397,11 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, nomem:hfi1_cdbg (TID ,"total mapped: tidpairs:%u pages:%u (%d)" , tididx, mapped_pages, ret); +/* adjust reserved tid_used to actual count */ +spin_lock (&fd->tid_lock); + fd->tid_used -= pageset_count - tididx; +spin_unlock (&fd->tid_lock);if (tididx) { -spin_lock (&fd->tid_lock); - fd->tid_used += tididx; -spin_unlock (&fd->tid_lock); tinfo->tidcnt = tididx; tinfo->length = mapped_pages *PAGE_SIZE ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 23/204 IB/hfi1: Fix expected receive setup error exit issues
In reply to Greg Kroah-HartmanFrom: Dean Luick <[email protected]>
[ Upstream commit e0c4a422f5246abefbf7c178ef99a1f2dc3c5f62 ]
Fix three error exit issues in expected receive setup. Re-arrange error exits to increase readability.
Issues and fixes:
1. Possible missed page unpin if tidlist copyout fails and not all pinned pages where made part of a TID.
Fix: Unpin the unused pages.
2. Return success with unset return values tidcnt and length when no pages were pinned.
Fix: Return -ENOSPC if no pages were pinned.
3. Return success with unset return values tidcnt and length when no rcvarray entries available.
Fix: Return -ENOSPC if no rcvarray entries are available.
--- drivers/infiniband/hw/hfi1/user_exp_rcv.c | 83 ++++++++++++++--------- 1 file changed, 50 insertions(+), 33 deletions(-)
drivers/infiniband/hw/hfi1/user_exp_rcv.c +50 -33
@@ -268,15 +268,14 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, tidbuf->psets =kcalloc (uctxt->expected_count,sizeof (*tidbuf->psets),GFP_KERNEL );if (!tidbuf->psets) { -kfree (tidbuf); -return -ENOMEM ; + ret = -ENOMEM ; + goto fail_release_mem; } pinned =pin_rcv_pages (fd, tidbuf);if (pinned <=0 ) { -kfree (tidbuf->psets); -kfree (tidbuf); -return pinned; + ret = (pinned <0 ) ? pinned : -ENOSPC ; + goto fail_unpin; }/* Find sets of physically contiguous pages */
@@ -291,14 +290,16 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, fd->tid_used += pageset_count;spin_unlock (&fd->tid_lock); -if (!pageset_count) - goto bail; +if (!pageset_count) { + ret = -ENOSPC ; + goto fail_unreserve; + } ngroups = pageset_count / dd->rcv_entries.group_size; tidlist =kcalloc (pageset_count,sizeof (*tidlist),GFP_KERNEL );if (!tidlist) { ret = -ENOMEM ; - goto nomem; + goto fail_unreserve; } tididx =0 ;
@@ -394,44 +395,60 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, } unlock:mutex_unlock (&uctxt->exp_mutex); -nomem:hfi1_cdbg (TID ,"total mapped: tidpairs:%u pages:%u (%d)" , tididx, mapped_pages, ret); + +/* fail if nothing was programmed, set error if none provided */ +if (tididx ==0 ) { +if (ret >=0 ) + ret = -ENOSPC ; + goto fail_unreserve; + } +/* adjust reserved tid_used to actual count */ spin_lock (&fd->tid_lock); fd->tid_used -= pageset_count - tididx;spin_unlock (&fd->tid_lock); -if (tididx) { - tinfo->tidcnt = tididx; - tinfo->length = mapped_pages *PAGE_SIZE ; -if (copy_to_user (u64_to_user_ptr (tinfo->tidlist), - tidlist,sizeof (tidlist[0 ]) * tididx)) { -/* -* On failure to copy to the user level, we need to undo -* everything done so far so we don't leak resources. -*/ - tinfo->tidlist = (unsigned long )&tidlist; -hfi1_user_exp_rcv_clear (fd, tinfo); - tinfo->tidlist =0 ; - ret = -EFAULT ; - goto bail; - } +/* unpin all pages not covered by a TID */ +unpin_rcv_pages (fd, tidbuf,NULL , mapped_pages, pinned - mapped_pages, + false); + + tinfo->tidcnt = tididx; + tinfo->length = mapped_pages *PAGE_SIZE ; + +if (copy_to_user (u64_to_user_ptr (tinfo->tidlist), + tidlist,sizeof (tidlist[0 ]) * tididx)) { + ret = -EFAULT ; + goto fail_unprogram; } -/* -* If not everything was mapped (due to insufficient RcvArray entries, -* for example), unpin all unmapped pages so we can pin them nex time. -*/ -if (mapped_pages != pinned) -unpin_rcv_pages (fd, tidbuf,NULL , mapped_pages, - (pinned - mapped_pages), false); -bail: +kfree (tidbuf->pages);kfree (tidbuf->psets); +kfree (tidbuf);kfree (tidlist); +return 0 ; + +fail_unprogram: +/* unprogram, unmap, and unpin all allocated TIDs */ + tinfo->tidlist = (unsigned long )tidlist; +hfi1_user_exp_rcv_clear (fd, tinfo); + tinfo->tidlist =0 ; + pinned =0 ;/* nothing left to unpin */ + pageset_count =0 ;/* nothing left reserved */ +fail_unreserve: +spin_lock (&fd->tid_lock); + fd->tid_used -= pageset_count; +spin_unlock (&fd->tid_lock); +fail_unpin: +if (pinned >0 ) +unpin_rcv_pages (fd, tidbuf,NULL ,0 , pinned, false); +fail_release_mem:kfree (tidbuf->pages); +kfree (tidbuf->psets);kfree (tidbuf); -return ret >0 ?0 : ret; +kfree (tidlist); +return ret; } int hfi1_user_exp_rcv_clear(struct hfi1_filedata *fd,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 24/204 IB/hfi1: Immediately remove invalid memory from hardware
In reply to Greg Kroah-HartmanFrom: Dean Luick <[email protected]>
[ Upstream commit 1c7edde1b5720ddb0aff5ca8c7f605a0f92526eb ]
When a user expected receive page is unmapped, it should be immediately removed from hardware rather than depend on a reaction from user space.
--- drivers/infiniband/hw/hfi1/user_exp_rcv.c | 43 +++++++++++++++-------- drivers/infiniband/hw/hfi1/user_exp_rcv.h | 1 + 2 files changed, 30 insertions(+), 14 deletions(-)
drivers/infiniband/hw/hfi1/user_exp_rcv.c +29 -14
@@ -28,8 +28,9 @@ static int program_rcvarray(struct hfi1_filedata *fd, struct tid_user_buf *, unsigned int start, u16 count, u32 *tidlist, unsigned int *tididx, unsigned int *pmapped); -static int unprogram_rcvarray (struct hfi1_filedata *fd,u32 tidinfo, -struct tid_group **grp); +static int unprogram_rcvarray (struct hfi1_filedata *fd,u32 tidinfo); +static void __clear_tid_node (struct hfi1_filedata *fd, +struct tid_rb_node *node);static void clear_tid_node (struct hfi1_filedata *fd,struct tid_rb_node *node);static const struct mmu_interval_notifier_ops tid_mn_ops = {
@@ -469,7 +470,7 @@ int hfi1_user_exp_rcv_clear(struct hfi1_filedata *fd,mutex_lock (&uctxt->exp_mutex);for (tididx =0 ; tididx < tinfo->tidcnt; tididx++) { - ret =unprogram_rcvarray (fd, tidinfo[tididx],NULL ); + ret =unprogram_rcvarray (fd, tidinfo[tididx]);if (ret) {hfi1_cdbg (TID ,"Failed to unprogram rcv array %d" , ret);
@@ -724,6 +725,7 @@ static int set_rcvarray_entry(struct hfi1_filedata *fd, } node->fdata = fd; +mutex_init (&node->invalidate_mutex); node->phys =page_to_phys (pages[0 ]); node->npages = npages; node->rcventry = rcventry;
@@ -763,8 +765,7 @@ static int set_rcvarray_entry(struct hfi1_filedata *fd,return -EFAULT ; } -static int unprogram_rcvarray (struct hfi1_filedata *fd,u32 tidinfo, -struct tid_group **grp) +static int unprogram_rcvarray (struct hfi1_filedata *fd,u32 tidinfo) {struct hfi1_ctxtdata *uctxt = fd->uctxt;struct hfi1_devdata *dd = uctxt->dd;
@@ -787,9 +788,6 @@ static int unprogram_rcvarray(struct hfi1_filedata *fd, u32 tidinfo,if (!node || node->rcventry != (uctxt->expected_base + rcventry))return -EBADF ; -if (grp) - *grp = node->grp; -if (fd->use_mn)mmu_interval_notifier_remove (&node->notifier);cacheless_tid_rb_remove (fd, node);
@@ -797,23 +795,34 @@ static int unprogram_rcvarray(struct hfi1_filedata *fd, u32 tidinfo,return 0 ; } -static void clear_tid_node (struct hfi1_filedata *fd,struct tid_rb_node *node) +static void __clear_tid_node (struct hfi1_filedata *fd,struct tid_rb_node *node) {struct hfi1_ctxtdata *uctxt = fd->uctxt;struct hfi1_devdata *dd = uctxt->dd; +mutex_lock (&node->invalidate_mutex); +if (node->freed) + goto done; + node->freed = true; +trace_hfi1_exp_tid_unreg (uctxt->ctxt, fd->subctxt, node->rcventry, node->npages, node->notifier.interval_tree.start, node->phys, node->dma_addr); -/* -* Make sure device has seen the write before we unpin the -* pages. -*/ +/* Make sure device has seen the write before pages are unpinned */ hfi1_put_tid (dd, node->rcventry,PT_INVALID_FLUSH ,0 ,0 );unpin_rcv_pages (fd,NULL , node,0 , node->npages, true); +done: +mutex_unlock (&node->invalidate_mutex); +} + +static void clear_tid_node (struct hfi1_filedata *fd,struct tid_rb_node *node) +{ +struct hfi1_ctxtdata *uctxt = fd->uctxt; + +__clear_tid_node (fd, node); node->grp->used--; node->grp->map &= ~(1 << (node->rcventry - node->grp->base));
@@ -872,10 +881,16 @@ static bool tid_rb_invalidate(struct mmu_interval_notifier *mni,if (node->freed)return true; +/* take action only if unmapping */ +if (range->event !=MMU_NOTIFY_UNMAP ) +return true; +trace_hfi1_exp_tid_inval (uctxt->ctxt, fdata->subctxt, node->notifier.interval_tree.start, node->rcventry, node->npages, node->dma_addr); - node->freed = true; + +/* clear the hardware rcvarray entry */ +__clear_tid_node (fdata, node);spin_lock (&fdata->invalid_lock);if (fdata->invalid_tid_idx < uctxt->expected_count) {
drivers/infiniband/hw/hfi1/user_exp_rcv.h +1 -0
@@ -27,6 +27,7 @@ struct tid_user_buf {struct tid_rb_node {struct mmu_interval_notifier notifier;struct hfi1_filedata *fdata; +struct mutex invalidate_mutex;/* covers hw removal */ unsigned long phys;struct tid_group *grp;u32 rcventry;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 25/204 IB/hfi1: Remove user expected buffer invalidate race
In reply to Greg Kroah-HartmanFrom: Dean Luick <[email protected]>
[ Upstream commit b3deec25847bda34e34d5d7be02f633caf000bd8 ]
During setup, there is a possible race between a page invalidate and hardware programming. Add a covering invalidate over the user target range during setup. If anything within that range is invalidated during setup, fail the setup. Once set up, each TID will have its own invalidate callback and invalidate.
--- drivers/infiniband/hw/hfi1/user_exp_rcv.c | 58 +++++++++++++++++++++-- drivers/infiniband/hw/hfi1/user_exp_rcv.h | 2 + 2 files changed, 55 insertions(+), 5 deletions(-)
drivers/infiniband/hw/hfi1/user_exp_rcv.c +53 -5
@@ -23,6 +23,9 @@ static void cacheless_tid_rb_remove(struct hfi1_filedata *fdata,static bool tid_rb_invalidate (struct mmu_interval_notifier *mni,const struct mmu_notifier_range *range,unsigned long cur_seq); +static bool tid_cover_invalidate (struct mmu_interval_notifier *mni, +const struct mmu_notifier_range *range, +unsigned long cur_seq); static int program_rcvarray(struct hfi1_filedata *fd, struct tid_user_buf *, struct tid_group *grp, unsigned int start, u16 count,
@@ -36,6 +39,9 @@ static void clear_tid_node(struct hfi1_filedata *fd, struct tid_rb_node *node);static const struct mmu_interval_notifier_ops tid_mn_ops = { .invalidate = tid_rb_invalidate, }; +static const struct mmu_interval_notifier_ops tid_cover_ops = { + .invalidate = tid_cover_invalidate, +};/* * Initialize context and file private data needed for Expected
@@ -254,6 +260,7 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, tididx =0 , mapped, mapped_pages =0 ;u32 *tidlist =NULL ;struct tid_user_buf *tidbuf; +unsigned long mmu_seq =0 ;if (!PAGE_ALIGNED (tinfo->vaddr))return -EINVAL ;
@@ -264,6 +271,7 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd,if (!tidbuf)return -ENOMEM ; +mutex_init (&tidbuf->cover_mutex); tidbuf->vaddr = tinfo->vaddr; tidbuf->length = tinfo->length; tidbuf->psets = kcalloc(uctxt->expected_count, sizeof(*tidbuf->psets),
@@ -273,6 +281,16 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, goto fail_release_mem; } +if (fd->use_mn) { + ret =mmu_interval_notifier_insert ( + &tidbuf->notifier, current->mm, + tidbuf->vaddr, tidbuf->npages *PAGE_SIZE , + &tid_cover_ops); +if (ret) + goto fail_release_mem; + mmu_seq =mmu_interval_read_begin (&tidbuf->notifier); + } + pinned =pin_rcv_pages (fd, tidbuf);if (pinned <=0 ) { ret = (pinned <0 ) ? pinned : -ENOSPC ;
@@ -415,6 +433,20 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd,unpin_rcv_pages (fd, tidbuf,NULL , mapped_pages, pinned - mapped_pages, false); +if (fd->use_mn) { +/* check for an invalidate during setup */ +bool fail = false; + +mutex_lock (&tidbuf->cover_mutex); + fail =mmu_interval_read_retry (&tidbuf->notifier, mmu_seq); +mutex_unlock (&tidbuf->cover_mutex); + +if (fail) { + ret = -EBUSY ; + goto fail_unprogram; + } + } + tinfo->tidcnt = tididx; tinfo->length = mapped_pages *PAGE_SIZE ;
@@ -424,6 +456,8 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, goto fail_unprogram; } +if (fd->use_mn) +mmu_interval_notifier_remove (&tidbuf->notifier);kfree (tidbuf->pages);kfree (tidbuf->psets);kfree (tidbuf);
@@ -442,6 +476,8 @@ int hfi1_user_exp_rcv_setup(struct hfi1_filedata *fd, fd->tid_used -= pageset_count;spin_unlock (&fd->tid_lock); fail_unpin: +if (fd->use_mn) +mmu_interval_notifier_remove (&tidbuf->notifier);if (pinned >0 )unpin_rcv_pages (fd, tidbuf,NULL ,0 , pinned, false); fail_release_mem:
@@ -741,11 +777,6 @@ static int set_rcvarray_entry(struct hfi1_filedata *fd, &tid_mn_ops);if (ret) goto out_unmap; -/* -* FIXME: This is in the wrong order, the notifier should be -* established before the pages are pinned by pin_rcv_pages. -*/ -mmu_interval_read_begin (&node->notifier); } fd->entry_to_rb[node->rcventry - uctxt->expected_base] = node;
@@ -920,6 +951,23 @@ static bool tid_rb_invalidate(struct mmu_interval_notifier *mni,return true; } +static bool tid_cover_invalidate (struct mmu_interval_notifier *mni, +const struct mmu_notifier_range *range, +unsigned long cur_seq) +{ +struct tid_user_buf *tidbuf = + container_of(mni, struct tid_user_buf, notifier); + +/* take action only if unmapping */ +if (range->event ==MMU_NOTIFY_UNMAP ) { +mutex_lock (&tidbuf->cover_mutex); +mmu_interval_set_seq (mni, cur_seq); +mutex_unlock (&tidbuf->cover_mutex); + } + +return true; +} +static void cacheless_tid_rb_remove (struct hfi1_filedata *fdata,struct tid_rb_node *tnode) {
drivers/infiniband/hw/hfi1/user_exp_rcv.h +2 -0
@@ -16,6 +16,8 @@ struct tid_pageset { };struct tid_user_buf { +struct mmu_interval_notifier notifier; +struct mutex cover_mutex;unsigned long vaddr;unsigned long length;unsigned int npages;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 26/204 affs: initialize fsdata in affs_truncate()
In reply to Greg Kroah-HartmanFrom: Alexander Potapenko <[email protected]>
[ Upstream commit eef034ac6690118c88f357b00e2b3239c9d8575d ]
When aops->write_begin() does not initialize fsdata, KMSAN may report an error passing the latter to aops->write_end().
Fix this by unconditionally initializing fsdata.
--- fs/affs/file.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
fs/affs/file.c +1 -1
@@ -881,7 +881,7 @@ affs_truncate(struct inode *inode)if (inode->i_size >AFFS_I (inode)->mmu_private) {struct address_space *mapping = inode->i_mapping;struct page *page; -void *fsdata; +void *fsdata =NULL ;loff_t isize = inode->i_size;int res;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 27/204 PM: AVS: qcom-cpr: Fix an error handling path in cpr_probe()
In reply to Greg Kroah-HartmanFrom: Christophe JAILLET <[email protected]>
[ Upstream commit 6049aae52392539e505bfb8ccbcff3c26f1d2f0b ]
If an error occurs after a successful pm_genpd_init() call, it should be undone by a corresponding pm_genpd_remove().
Add the missing call in the error handling path, as already done in the remove function.
--- drivers/soc/qcom/cpr.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/soc/qcom/cpr.c +5 -1
@@ -1710,12 +1710,16 @@ static int cpr_probe(struct platform_device *pdev) ret =of_genpd_add_provider_simple (dev->of_node, &drv->pd);if (ret) -return ret; + goto err_remove_genpd;platform_set_drvdata (pdev, drv);cpr_debugfs_init (drv);return 0 ; + +err_remove_genpd: +pm_genpd_remove (&drv->pd); +return ret; }static int cpr_remove (struct platform_device *pdev)
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 28/204 arm64: dts: qcom: msm8992: Dont use sfpb mutex
In reply to Greg Kroah-HartmanFrom: Konrad Dybcio <[email protected]>
[ Upstream commit 2bd5ab93335bf2c4d22c8db427822ae637ed8dc3 ]
MSM8992 uses the same mutex hardware as MSM8994. This was wrong from the start, but never presented as an issue until the sfpb compatible was given different driver data.
--- arch/arm64/boot/dts/qcom/msm8992.dtsi | 4 ---- 1 file changed, 4 deletions(-)
arch/arm64/boot/dts/qcom/msm8992.dtsi +0 -4
@@ -14,10 +14,6 @@ &rpmcc { compatible = "qcom,rpmcc-msm8992"; }; -&tcsr_mutex { - compatible = "qcom,sfpb-mutex"; -}; - &timer { interrupts = <GIC_PPI 2 (GIC_CPU_MASK_SIMPLE(4) | IRQ_TYPE_LEVEL_LOW)>, <GIC_PPI 3 (GIC_CPU_MASK_SIMPLE(4) | IRQ_TYPE_LEVEL_LOW)>,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 29/204 arm64: dts: qcom: msm8992-libra: Add CPU regulators
In reply to Greg Kroah-HartmanFrom: Konrad Dybcio <[email protected]>
[ Upstream commit 13cff03303676148bc8f0bbe73a6d40d5fdd020e ]
Specify CPU regulator voltages for both VDD_APC rails.
Stable-dep-of: 69876bc6fd4d ("arm64: dts: qcom: msm8992-libra: Fix the memory map")
--- .../boot/dts/qcom/msm8992-xiaomi-libra.dts | 17 +++++++++++++++++ 1 file changed, 17 insertions(+)
arch/arm64/boot/dts/qcom/msm8992-xiaomi-libra.dts +17 -0
@@ -125,6 +125,23 @@ &peripheral_region { no-map; }; +&pm8994_spmi_regulators { + VDD_APC0: s8 { + regulator-min-microvolt = <680000>; + regulator-max-microvolt = <1180000>; + regulator-always-on; + regulator-boot-on; + }; + + /* APC1 is 3-phase, but quoting downstream, s11 is "the gang leader" */ + VDD_APC1: s11 { + regulator-min-microvolt = <700000>; + regulator-max-microvolt = <1225000>; + regulator-always-on; + regulator-boot-on; + }; +}; + &rpm_requests { pm8994-regulators { compatible = "qcom,rpm-pm8994-regulators";
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 30/204 arm64: dts: qcom: msm8992-libra: Fix the memory map
In reply to Greg Kroah-HartmanFrom: Konrad Dybcio <[email protected]>
[ Upstream commit 69876bc6fd4de3ad2dc7826fe269e91fa2c1807f ]
The memory map was wrong. Fix it to prevent the device from randomly rebooting.
--- .../boot/dts/qcom/msm8992-xiaomi-libra.dts | 77 +++++++++++++++---- 1 file changed, 60 insertions(+), 17 deletions(-)
arch/arm64/boot/dts/qcom/msm8992-xiaomi-libra.dts +60 -17
@@ -11,6 +11,12 @@ #include <dt-bindings/gpio/gpio.h> #include <dt-bindings/input/gpio-keys.h> +/delete-node/ &adsp_mem; +/delete-node/ &audio_mem; +/delete-node/ &mpss_mem; +/delete-node/ &peripheral_region; +/delete-node/ &rmtfs_mem; + / { model = "Xiaomi Mi 4C"; compatible = "xiaomi,libra", "qcom,msm8992";
@@ -60,25 +66,67 @@ reserved-memory { #size-cells = <2>; ranges; - /* This is for getting crash logs using Android downstream kernels */ - ramoops@dfc00000 { - compatible = "ramoops"; - reg = <0x0 0xdfc00000 0x0 0x40000>; - console-size = <0x10000>; - record-size = <0x10000>; - ftrace-size = <0x10000>; - pmsg-size = <0x20000>; + memory_hole: hole@6400000 { + reg = <0 0x06400000 0 0x600000>; + no-map; + }; + + memory_hole2: hole2@6c00000 { + reg = <0 0x06c00000 0 0x2400000>; + no-map; + }; + + mpss_mem: mpss@9000000 { + reg = <0 0x09000000 0 0x5a00000>; + no-map; + }; + + tzapp: tzapp@ea00000 { + reg = <0 0x0ea00000 0 0x1900000>; + no-map; + }; + + mdm_rfsa_mem: mdm-rfsa@ca0b0000 { + reg = <0 0xca0b0000 0 0x10000>; + no-map; + }; + + rmtfs_mem: rmtfs@ca100000 { + compatible = "qcom,rmtfs-mem"; + reg = <0 0xca100000 0 0x180000>; + no-map; + + qcom,client-id = <1>; }; - modem_region: modem_region@9000000 { - reg = <0x0 0x9000000 0x0 0x5a00000>; + audio_mem: audio@cb400000 { + reg = <0 0xcb000000 0 0x400000>; + no-mem; + }; + + qseecom_mem: qseecom@cb400000 { + reg = <0 0xcb400000 0 0x1c00000>; + no-mem; + }; + + adsp_rfsa_mem: adsp-rfsa@cd000000 { + reg = <0 0xcd000000 0 0x10000>; no-map; }; - tzapp: modem_region@ea00000 { - reg = <0x0 0xea00000 0x0 0x1900000>; + sensor_rfsa_mem: sensor-rfsa@cd010000 { + reg = <0 0xcd010000 0 0x10000>; no-map; }; + + ramoops@dfc00000 { + compatible = "ramoops"; + reg = <0 0xdfc00000 0 0x40000>; + console-size = <0x10000>; + record-size = <0x10000>; + ftrace-size = <0x10000>; + pmsg-size = <0x20000>; + }; }; };
@@ -120,11 +168,6 @@ &blsp2_uart2 { status = "okay"; }; -&peripheral_region { - reg = <0x0 0x7400000 0x0 0x1c00000>; - no-map; -}; - &pm8994_spmi_regulators { VDD_APC0: s8 { regulator-min-microvolt = <680000>;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 31/204 phy: ti: fix Kconfig warning and operator precedence
In reply to Greg Kroah-HartmanFrom: Randy Dunlap <[email protected]>
[ Upstream commit 7124c93887cc4e6c5b48920f83115e4a5892e870 ]
Fix Kconfig depends operator precedence to prevent a Kconfig warning:
WARNING: unmet direct dependencies detected for MUX_MMIO
Depends on [n]: MULTIPLEXER [=m] && OF [=n]
Selected by [m]:
- PHY_AM654_SERDES [=m] && (OF [=n] && ARCH_K3 || COMPILE_TEST [=y]) && COMMON_CLK [=y]
--- drivers/phy/ti/Kconfig | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/phy/ti/Kconfig +2 -2
@@ -23,7 +23,7 @@ config PHY_DM816X_USB config PHY_AM654_SERDES tristate "TI AM654 SERDES support" - depends on OF && ARCH_K3 || COMPILE_TEST + depends on OF && (ARCH_K3 || COMPILE_TEST) depends on COMMON_CLK select GENERIC_PHY select MULTIPLEXER
@@ -35,7 +35,7 @@ config PHY_AM654_SERDES config PHY_J721E_WIZ tristate "TI J721E WIZ (SERDES Wrapper) support" - depends on OF && ARCH_K3 || COMPILE_TEST + depends on OF && (ARCH_K3 || COMPILE_TEST) depends on HAS_IOMEM && OF_ADDRESS depends on COMMON_CLK select GENERIC_PHY
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 32/204 NFSD: fix use-after-free in nfsd4_ssc_setup_dul()
In reply to Greg Kroah-HartmanFrom: Xingyuan Mo <[email protected]>
[ Upstream commit e6cf91b7b47ff82b624bdfe2fdcde32bb52e71dd ]
If signal_pending() returns true, schedule_timeout() will not be executed, causing the waiting task to remain in the wait queue.
Fixed by adding a call to finish_wait(), which ensures that the waiting task will always be removed from the wait queue.
--- fs/nfsd/nfs4proc.c | 1 + 1 file changed, 1 insertion(+)
fs/nfsd/nfs4proc.c +1 -0
@@ -1205,6 +1205,7 @@ static __be32 nfsd4_ssc_setup_dul(struct nfsd_net *nn, char *ipaddr,/* allow 20secs for mount/unmount for now - revisit */ if (signal_pending (current) || (schedule_timeout (20 *HZ ) ==0 )) { +finish_wait (&nn->nfsd_ssc_waitq, &wait);kfree (work);return nfserr_eagain; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 33/204 ARM: dts: at91: sam9x60: fix the ddr clock for sam9x60
In reply to Greg Kroah-HartmanFrom: Claudiu Beznea <[email protected]>
[ Upstream commit 9bfa2544dbd1133f0b0af4e967de3bb9c1e3a497 ]
The 2nd DDR clock for sam9x60 DDR controller is peripheral clock with id 49.
--- arch/arm/boot/dts/sam9x60.dtsi | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/arm/boot/dts/sam9x60.dtsi +1 -1
@@ -567,7 +567,7 @@ pmecc: ecc-engine@ffffe000 { mpddrc: mpddrc@ffffe800 { compatible = "microchip,sam9x60-ddramc", "atmel,sama5d3-ddramc"; reg = <0xffffe800 0x200>; - clocks = <&pmc PMC_TYPE_SYSTEM 2>, <&pmc PMC_TYPE_CORE PMC_MCK>; + clocks = <&pmc PMC_TYPE_SYSTEM 2>, <&pmc PMC_TYPE_PERIPHERAL 49>; clock-names = "ddrck", "mpddr"; };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 34/204 amd-xgbe: TX Flow Ctrl Registers are h/w ver dependent
In reply to Greg Kroah-HartmanFrom: Raju Rangoju <[email protected]>
[ Upstream commit 579923d84b04abb6cd4cd1fd9974096a2dd1832b ]
There is difference in the TX Flow Control registers (TFCR) between the revisions of the hardware. The older revisions of hardware used to have single register per queue. Whereas, the newer revision of hardware (from ver 30H onwards) have one register per priority.
Update the driver to use the TFCR based on the reported version of the hardware.
--- drivers/net/ethernet/amd/xgbe/xgbe-dev.c | 23 +++++++++++++++-------- 1 file changed, 15 insertions(+), 8 deletions(-)
drivers/net/ethernet/amd/xgbe/xgbe-dev.c +15 -8
@@ -524,19 +524,28 @@ static void xgbe_disable_vxlan(struct xgbe_prv_data *pdata)netif_dbg (pdata, drv, pdata->netdev,"VXLAN acceleration disabled\n" ); } +static unsigned int xgbe_get_fc_queue_count (struct xgbe_prv_data *pdata) +{ +unsigned int max_q_count =XGMAC_MAX_FLOW_CONTROL_QUEUES ; + +/* From MAC ver 30H the TFCR is per priority, instead of per queue */ +if (XGMAC_GET_BITS (pdata->hw_feat.version,MAC_VR ,SNPSVER ) >=0x30 ) +return max_q_count; +else + return min_t(unsigned int, pdata->tx_q_count, max_q_count); +} +static int xgbe_disable_tx_flow_control (struct xgbe_prv_data *pdata) { -unsigned int max_q_count, q_count;unsigned int reg, reg_val; -unsigned int i; +unsigned int i, q_count;/* Clear MTL flow control */ for (i =0 ; i < pdata->rx_q_count; i++)XGMAC_MTL_IOWRITE_BITS (pdata, i,MTL_Q_RQOMR ,EHFC ,0 );/* Clear MAC flow control */ - max_q_count =XGMAC_MAX_FLOW_CONTROL_QUEUES ; - q_count = min_t(unsigned int, pdata->tx_q_count, max_q_count); + q_count =xgbe_get_fc_queue_count (pdata); reg =MAC_Q0TFCR ;for (i =0 ; i < q_count; i++) { reg_val =XGMAC_IOREAD (pdata, reg);
@@ -553,9 +562,8 @@ static int xgbe_enable_tx_flow_control(struct xgbe_prv_data *pdata) {struct ieee_pfc *pfc = pdata->pfc;struct ieee_ets *ets = pdata->ets; -unsigned int max_q_count, q_count;unsigned int reg, reg_val; -unsigned int i; +unsigned int i, q_count;/* Set MTL flow control */ for (i =0 ; i < pdata->rx_q_count; i++) {
@@ -579,8 +587,7 @@ static int xgbe_enable_tx_flow_control(struct xgbe_prv_data *pdata) }/* Set MAC flow control */ - max_q_count =XGMAC_MAX_FLOW_CONTROL_QUEUES ; - q_count = min_t(unsigned int, pdata->tx_q_count, max_q_count); + q_count =xgbe_get_fc_queue_count (pdata); reg =MAC_Q0TFCR ;for (i =0 ; i < q_count; i++) { reg_val =XGMAC_IOREAD (pdata, reg);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 35/204 amd-xgbe: Delay AN timeout during KR training
In reply to Greg Kroah-HartmanFrom: Raju Rangoju <[email protected]>
[ Upstream commit 926446ae24c03311a480fb96eb78f0ce7ea6d091 ]
AN restart triggered during KR training not only aborts the KR training process but also move the HW to unstable state. Driver has to wait upto 500ms or until the KR training is completed before restarting AN cycle.
--- drivers/net/ethernet/amd/xgbe/xgbe-mdio.c | 24 +++++++++++++++++++++++ drivers/net/ethernet/amd/xgbe/xgbe.h | 2 ++ 2 files changed, 26 insertions(+)
drivers/net/ethernet/amd/xgbe/xgbe-mdio.c +24 -0
@@ -496,6 +496,7 @@ static enum xgbe_an xgbe_an73_tx_training(struct xgbe_prv_data *pdata, reg |=XGBE_KR_TRAINING_ENABLE ; reg |=XGBE_KR_TRAINING_START ;XMDIO_WRITE (pdata,MDIO_MMD_PMAPMD ,MDIO_PMA_10GBR_PMD_CTRL , reg); + pdata->kr_start_time = jiffies;netif_dbg (pdata, link, pdata->netdev,"KR training initiated\n" );
@@ -632,6 +633,8 @@ static enum xgbe_an xgbe_an73_incompat_link(struct xgbe_prv_data *pdata)xgbe_switch_mode (pdata); + pdata->an_result =XGBE_AN_READY ; +xgbe_an_restart (pdata);return XGBE_AN_INCOMPAT_LINK ;
@@ -1275,9 +1278,30 @@ static bool xgbe_phy_aneg_done(struct xgbe_prv_data *pdata)static void xgbe_check_link_timeout (struct xgbe_prv_data *pdata) {unsigned long link_timeout; +unsigned long kr_time; +int wait; link_timeout = pdata->link_check + (XGBE_LINK_TIMEOUT *HZ );if (time_after (jiffies, link_timeout)) { +if ((xgbe_cur_mode (pdata) ==XGBE_MODE_KR ) && + pdata->phy.autoneg ==AUTONEG_ENABLE ) { +/* AN restart should not happen while KR training is in progress. +* The while loop ensures no AN restart during KR training, +* waits up to 500ms and AN restart is triggered only if KR +* training is failed. +*/ + wait =XGBE_KR_TRAINING_WAIT_ITER ; +while (wait--) { + kr_time = pdata->kr_start_time + +msecs_to_jiffies (XGBE_AN_MS_TIMEOUT ); +if (time_after (jiffies, kr_time)) +break ; +/* AN restart is not required, if AN result is COMPLETE */ +if (pdata->an_result ==XGBE_AN_COMPLETE ) +return ; +usleep_range (10000 ,11000 ); + } + }netif_dbg (pdata, link, pdata->netdev,"AN link timeout\n" );xgbe_phy_config_aneg (pdata); }
drivers/net/ethernet/amd/xgbe/xgbe.h +2 -0
@@ -289,6 +289,7 @@/* Auto-negotiation */ #define XGBE_AN_MS_TIMEOUT 500#define XGBE_LINK_TIMEOUT 5 +#define XGBE_KR_TRAINING_WAIT_ITER 50#define XGBE_SGMII_AN_LINK_STATUS BIT(1)#define XGBE_SGMII_AN_LINK_SPEED (BIT(2) | BIT(3))
@@ -1253,6 +1254,7 @@ struct xgbe_prv_data {unsigned int parallel_detect;unsigned int fec_ability;unsigned long an_start; +unsigned long kr_start_time;enum xgbe_an_mode an_mode;/* I2C support */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 36/204 bpf: Fix pointer-leak due to insufficient speculative store bypass mitigation
In reply to Greg Kroah-HartmanFrom: Luis Gerhorst <[email protected]>
[ Upstream commit e4f4db47794c9f474b184ee1418f42e6a07412b6 ]
To mitigate Spectre v4, 2039f26f3aca ("bpf: Fix leakage due to insufficient speculative store bypass mitigation") inserts lfence instructions after 1) initializing a stack slot and 2) spilling a pointer to the stack.
However, this does not cover cases where a stack slot is first initialized with a pointer (subject to sanitization) but then overwritten with a scalar (not subject to sanitization because the slot was already initialized). In this case, the second write may be subject to speculative store bypass (SSB) creating a speculative pointer-as-scalar type confusion. This allows the program to subsequently leak the numerical pointer value using, for example, a branch-based cache side channel.
To fix this, also sanitize scalars if they write a stack slot that previously contained a pointer. Assuming that pointer-spills are only generated by LLVM on register-pressure, the performance impact on most real-world BPF programs should be small.
The following unprivileged BPF bytecode drafts a minimal exploit and the mitigation:
[...]
// r6 = 0 or 1 (skalar, unknown user input)
// r7 = accessible ptr for side channel
// r10 = frame pointer (fp), to be leaked
//
r9 = r10 # fp alias to encourage ssb
*(u64 *)(r9 - 8) = r10 // fp[-8] = ptr, to be leaked
// lfence added here because of pointer spill to stack.
//
// Ommitted: Dummy bpf_ringbuf_output() here to train alias predictor // for no r9-r10 dependency.
//
*(u64 *)(r10 - 8) = r6 // fp[-8] = scalar, overwrites ptr
// 2039f26f3aca: no lfence added because stack slot was not STACK_INVALID, // store may be subject to SSB
//
// fix: also add an lfence when the slot contained a ptr
//
r8 = *(u64 *)(r9 - 8)
// r8 = architecturally a scalar, speculatively a ptr
//
// leak ptr using branch-based cache side channel:
r8 &= 1 // choose bit to leak
if r8 == 0 goto SLOW // no mispredict
// architecturally dead code if input r6 is 0,
// only executes speculatively iff ptr bit is 1
r8 = *(u64 *)(r7 + 0) # encode bit in cache (0: slow, 1: fast)
SLOW:
[...]
After running this, the program can time the access to *(r7 + 0) to determine whether the chosen pointer bit was 0 or 1. Repeat this 64 times to recover the whole address on amd64.
In summary, sanitization can only be skipped if one scalar is overwritten with another scalar. Scalar-confusion due to speculative store bypass can not lead to invalid accesses because the pointer bounds deducted during verification are enforced using branchless logic. See 979d63d50c0c ("bpf: prevent out of bounds speculation on pointer arithmetic") for details.
Do not make the mitigation depend on !env->allow_{uninit_stack,ptr_leaks} because speculative leaks are likely unexpected if these were enabled. For example, leaking the address to a protected log file may be acceptable while disabling the mitigation might unintentionally leak the address into the cached-state of a map that is accessible to unprivileged processes.
--- kernel/bpf/verifier.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
kernel/bpf/verifier.c +3 -1
@@ -2653,7 +2653,9 @@ static int check_stack_write_fixed_off(struct bpf_verifier_env *env,bool sanitize = reg &&is_spillable_regtype (reg->type);for (i =0 ; i < size; i++) { -if (state->stack[spi].slot_type[i] ==STACK_INVALID ) { +u8 type = state->stack[spi].slot_type[i]; + +if (type !=STACK_MISC && type !=STACK_ZERO ) { sanitize = true;break ; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 37/204 phy: rockchip-inno-usb2: Fix missing clk_disable_unprepare() in rockchip_usb2phy_power_on()
In reply to Greg Kroah-HartmanFrom: Shang XiaoJing <[email protected]>
[ Upstream commit 5daba914da0e48950e9407ea4d75fa57029c9adc ]
The clk_disable_unprepare() should be called in the error handling of rockchip_usb2phy_power_on().
--- drivers/phy/rockchip/phy-rockchip-inno-usb2.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/phy/rockchip/phy-rockchip-inno-usb2.c +3 -1
@@ -467,8 +467,10 @@ static int rockchip_usb2phy_power_on(struct phy *phy)return ret; ret =property_enable (base, &rport->port_cfg->phy_sus, false); -if (ret) +if (ret) { +clk_disable_unprepare (rphy->clk480m);return ret; + }/* waiting for the utmi_clk to become stable */ usleep_range (1500 ,2000 );
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 38/204 net: nfc: Fix use-after-free in local_cleanup()
In reply to Greg Kroah-HartmanFrom: Jisoo Jang <[email protected]>
[ Upstream commit 4bb4db7f3187c6e3de6b229ffc87cdb30a2d22b6 ]
Fix a use-after-free that occurs in kfree_skb() called from local_cleanup(). This could happen when killing nfc daemon (e.g. neard) after detaching an nfc device.
When detaching an nfc device, local_cleanup() called from nfc_llcp_unregister_device() frees local->rx_pending and decreases local->ref by kref_put() in nfc_llcp_local_put().
In the terminating process, nfc daemon releases all sockets and it leads to decreasing local->ref. After the last release of local->ref, local_cleanup() called from local_release() frees local->rx_pending again, which leads to the bug.
Setting local->rx_pending to NULL in local_cleanup() could prevent use-after-free when local_cleanup() is called twice.
Found by a modified version of syzkaller.
BUG: KASAN: use-after-free in kfree_skb() Call Trace:
dump_stack_lvl (lib/dump_stack.c:106) print_address_description.constprop.0.cold (mm/kasan/report.c:306) kasan_check_range (mm/kasan/generic.c:189)kfree_skb (net/core/skbuff.c:955)local_cleanup (net/nfc/llcp_core.c:159) nfc_llcp_local_put.part.0 (net/nfc/llcp_core.c:172) nfc_llcp_local_put (net/nfc/llcp_core.c:181) llcp_sock_destruct (net/nfc/llcp_sock.c:959) __sk_destruct (net/core/sock.c:2133)sk_destruct (net/core/sock.c:2181)__sk_free (net/core/sock.c:2192)sk_free (net/core/sock.c:2203)llcp_sock_release (net/nfc/llcp_sock.c:646) __sock_release (net/socket.c:650)sock_close (net/socket.c:1365)__fput (fs/file_table.c:306)task_work_run (kernel/task_work.c:179)ptrace_notify (kernel/signal.c:2354) syscall_exit_to_user_mode_prepare (kernel/entry/common.c:278) syscall_exit_to_user_mode (kernel/entry/common.c:296) do_syscall_64 (arch/x86/entry/common.c:86) entry_SYSCALL_64_after_hwframe (arch/x86/entry/entry_64.S:106)
Allocated by task 4719:
kasan_save_stack (mm/kasan/common.c:45) __kasan_slab_alloc (mm/kasan/common.c:325) slab_post_alloc_hook (mm/slab.h:766) kmem_cache_alloc_node (mm/slub.c:3497) __alloc_skb (net/core/skbuff.c:552) pn533_recv_response (drivers/nfc/pn533/usb.c:65) __usb_hcd_giveback_urb (drivers/usb/core/hcd.c:1671) usb_giveback_urb_bh (drivers/usb/core/hcd.c:1704) tasklet_action_common.isra.0 (kernel/softirq.c:797) __do_softirq (kernel/softirq.c:571)
Freed by task 1901:
kasan_save_stack (mm/kasan/common.c:45) kasan_set_track (mm/kasan/common.c:52) kasan_save_free_info (mm/kasan/genericdd.c:518) __kasan_slab_free (mm/kasan/common.c:236) kmem_cache_free (mm/slub.c:3809)kfree_skbmem (net/core/skbuff.c:874)kfree_skb (net/core/skbuff.c:931) local_cleanup (net/nfc/llcp_core.c:159) nfc_llcp_unregister_device (net/nfc/llcp_core.c:1617) nfc_unregister_device (net/nfc/core.c:1179) pn53x_unregister_nfc (drivers/nfc/pn533/pn533.c:2846) pn533_usb_disconnect (drivers/nfc/pn533/usb.c:579) usb_unbind_interface (drivers/usb/core/driver.c:458) device_release_driver_internal (drivers/base/dd.c:1279) bus_remove_device (drivers/base/bus.c:529) device_del (drivers/base/core.c:3665) usb_disable_device (drivers/usb/core/message.c:1420) usb_disconnect (drivers/usb/core.c:2261) hub_event (drivers/usb/core/hub.c:5833)
process_one_work (arch/x86/include/asm/jump_label.h:27 include/linux/jump_label.h:212 include/trace/events/workqueue.h:108 kernel/workqueue.c:2281) worker_thread (include/linux/list.h:282 kernel/workqueue.c:2423)
kthread (kernel/kthread.c:319)ret_from_fork (arch/x86/entry/entry_64.S:301)
--- net/nfc/llcp_core.c | 1 + 1 file changed, 1 insertion(+)
net/nfc/llcp_core.c +1 -0
@@ -159,6 +159,7 @@ static void local_cleanup(struct nfc_llcp_local *local)cancel_work_sync (&local->rx_work);cancel_work_sync (&local->timeout_work);kfree_skb (local->rx_pending); + local->rx_pending =NULL ;del_timer_sync (&local->sdreq_timer);cancel_work_sync (&local->sdreq_timeout_work);nfc_llcp_free_sdp_tlv_list (&local->pending_sdreqs);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 39/204 net: wan: Add checks for NULL for utdm in undo_uhdlc_init and unmap_si_regs
In reply to Greg Kroah-HartmanFrom: Esina Ekaterina <[email protected]>
[ Upstream commit 488e0bf7f34af3d42d1d5e56f7a5a7beaff188a3 ]
If uhdlc_priv_tsa != 1 then utdm is not initialized. And if ret != NULL then goto undo_uhdlc_init, where utdm is dereferenced. Same if dev == NULL.
Found by Astra Linux on behalf of Linux Verification Center (linuxtesting.org) with SVACE.
--- drivers/net/wan/fsl_ucc_hdlc.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
drivers/net/wan/fsl_ucc_hdlc.c +4 -2
@@ -1241,9 +1241,11 @@ static int ucc_hdlc_probe(struct platform_device *pdev) free_dev:free_netdev (dev); undo_uhdlc_init: -iounmap (utdm->siram); +if (utdm) +iounmap (utdm->siram); unmap_si_regs: -iounmap (utdm->si_regs); +if (utdm) +iounmap (utdm->si_regs); free_utdm:if (uhdlc_priv->tsa)kfree (utdm);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 40/204 net: enetc: avoid deadlock in enetc_tx_onestep_tstamp()
In reply to Greg Kroah-HartmanFrom: Vladimir Oltean <[email protected]>
[ Upstream commit 3c463721a73bdb57a913e0d3124677a3758886fc ]
This lockdep splat says it better than I could:
================================
WARNING: inconsistent lock state 6.2.0-rc2-07010-ga9b9500ffaac-dirty #967 Not tainted
--------------------------------
inconsistent {IN-SOFTIRQ-W} -> {SOFTIRQ-ON-W} usage. kworker/1:3/179 [HC0[0]:SC0[0]:HE1:SE1] takes:ffff3ec4036ce098 (_xmit_ETHER#2){+.?.}-{3:3}, at: netif_freeze_queues+0x5c/0xc0 {IN-SOFTIRQ-W} state was registered at:
_raw_spin_lock+0x5c/0xc0 sch_direct_xmit+0x148/0x37c __dev_queue_xmit+0x528/0x111c ip6_finish_output2+0x5ec/0xb7c ip6_finish_output+0x240/0x3f0 ip6_output+0x78/0x360 ndisc_send_skb+0x33c/0x85c ndisc_send_rs+0x54/0x12c addrconf_rs_timer+0x154/0x260 call_timer_fn+0xb8/0x3a0 __run_timers.part.0+0x214/0x26c run_timer_softirq+0x3c/0x74 __do_softirq+0x14c/0x5d8 ____do_softirq+0x10/0x20 call_on_irq_stack+0x2c/0x5c do_softirq_own_stack+0x1c/0x30 __irq_exit_rcu+0x168/0x1a0 irq_exit_rcu+0x10/0x40 el1_interrupt+0x38/0x64 irq event stamp: 7825 hardirqs last enabled at (7825): [<ffffdf1f7200cae4>] exit_to_kernel_mode+0x34/0x130 hardirqs last disabled at (7823): [<ffffdf1f708105f0>] __do_softirq+0x550/0x5d8 softirqs last enabled at (7824): [<ffffdf1f7081050c>] __do_softirq+0x46c/0x5d8 softirqs last disabled at (7811): [<ffffdf1f708166e0>] ____do_softirq+0x10/0x20
other info that might help us debug this:
Possible unsafe locking scenario:
CPU0
----
lock(_xmit_ETHER#2);
<Interrupt>
lock(_xmit_ETHER#2);*** DEADLOCK ***
3 locks held by kworker/1:3/179:
#0: ffff3ec400004748 ((wq_completion)events){+.+.}-{0:0}, at: process_one_work+0x1f4/0x6c0
#1: ffff80000a0bbdc8 ((work_completion)(&priv->tx_onestep_tstamp)){+.+.}-{0:0}, at: process_one_work+0x1f4/0x6c0 #2: ffff3ec4036cd438 (&dev->tx_global_lock){+.+.}-{3:3}, at: netif_tx_lock+0x1c/0x34
Workqueue: events enetc_tx_onestep_tstamp Call trace: print_usage_bug.part.0+0x208/0x22c mark_lock+0x7f0/0x8b0 __lock_acquire+0x7c4/0x1ce0 lock_acquire.part.0+0xe0/0x220 lock_acquire+0x68/0x84 _raw_spin_lock+0x5c/0xc0 netif_freeze_queues+0x5c/0xc0 netif_tx_lock+0x24/0x34 enetc_tx_onestep_tstamp+0x20/0x100 process_one_work+0x28c/0x6c0 worker_thread+0x74/0x450 kthread+0x118/0x11c
but I'll say it anyway: the enetc_tx_onestep_tstamp() work item runs in process context, therefore with softirqs enabled (i.o.w., it can be interrupted by a softirq). If we hold the netif_tx_lock() when there is an interrupt, and the NET_TX softirq then gets scheduled, this will take the netif_tx_lock() a second time and deadlock the kernel.
To solve this, use netif_tx_lock_bh(), which blocks softirqs from running.
--- drivers/net/ethernet/freescale/enetc/enetc.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/net/ethernet/freescale/enetc/enetc.c +2 -2
@@ -2000,14 +2000,14 @@ static void enetc_tx_onestep_tstamp(struct work_struct *work) priv = container_of(work, struct enetc_ndev_priv, tx_onestep_tstamp); -netif_tx_lock (priv->ndev); +netif_tx_lock_bh (priv->ndev);clear_bit_unlock (ENETC_TX_ONESTEP_TSTAMP_IN_PROGRESS , &priv->flags); skb =skb_dequeue (&priv->tx_skbs);if (skb)enetc_start_xmit (skb, priv->ndev); -netif_tx_unlock (priv->ndev); +netif_tx_unlock_bh (priv->ndev); }static void enetc_tx_onestep_tstamp_init (struct enetc_ndev_priv *priv)
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 41/204 sch_htb: Avoid grafting on htb_destroy_class_offload when destroying htb
In reply to Greg Kroah-HartmanFrom: Rahul Rameshbabu <[email protected]>
[ Upstream commit a22b7388d658ecfcd226600c8c34ce4481e88655 ]
Peek at old qdisc and graft only when deleting a leaf class in the htb, rather than when deleting the htb itself. Do not peek at the qdisc of the netdev queue when destroying the htb. The caller may already have grafted a new qdisc that is not part of the htb structure being destroyed.
This fix resolves two use cases.
1. Using tc to destroy the htb.
- Netdev was being prematurely activated before the htb was fully destroyed.
2. Using tc to replace the htb with another qdisc (which also leads to the htb being destroyed).
- Premature netdev activation like previous case. Newly grafted qdisc was also getting accidentally overwritten when destroying the htb.
--- net/sched/sch_htb.c | 27 ++++++++++++++++----------- 1 file changed, 16 insertions(+), 11 deletions(-)
net/sched/sch_htb.c +16 -11
@@ -1558,7 +1558,7 @@ static int htb_destroy_class_offload(struct Qdisc *sch, struct htb_class *cl,struct tc_htb_qopt_offload offload_opt;struct netdev_queue *dev_queue;struct Qdisc *q = cl->leaf.q; -struct Qdisc *old =NULL ; +struct Qdisc *old;int err;if (cl->level)
@@ -1566,14 +1566,17 @@ static int htb_destroy_class_offload(struct Qdisc *sch, struct htb_class *cl,WARN_ON (!q); dev_queue =htb_offload_get_queue (cl); - old =htb_graft_helper (dev_queue,NULL ); -if (destroying) -/* Before HTB is destroyed, the kernel grafts noop_qdisc to -* all queues. +/* When destroying, caller qdisc_graft grafts the new qdisc and invokes +* qdisc_put for the qdisc being destroyed. htb_destroy_class_offload +* does not need to graft or qdisc_put the qdisc being destroyed. +*/ +if (!destroying) { + old =htb_graft_helper (dev_queue,NULL ); +/* Last qdisc grafted should be the same as cl->leaf.q when +* calling htb_delete. */ -WARN_ON (!(old->flags &TCQ_F_BUILTIN )); -else WARN_ON (old != q); + }if (cl->parent) { cl->parent->bstats_bias.bytes += q->bstats.bytes;
@@ -1589,10 +1592,12 @@ static int htb_destroy_class_offload(struct Qdisc *sch, struct htb_class *cl, }; err =htb_offload (qdisc_dev (sch), &offload_opt); -if (!err || destroying) -qdisc_put (old); -else -htb_graft_helper (dev_queue, old); +if (!destroying) { +if (!err) +qdisc_put (old); +else +htb_graft_helper (dev_queue, old); + }if (last_child)return err;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 42/204 gpio: use raw spinlock for gpio chip shadowed data
In reply to Greg Kroah-HartmanFrom: Schspa Shi <[email protected]>
[ Upstream commit 3c938cc5cebcbd2291fe97f523c0705a2c24c77d ]
In case of PREEMPT_RT, there is a raw_spinlock -> spinlock dependency as the lockdep report shows.
__irq_set_handler
irq_get_desc_buslock
__irq_get_desc_lock
raw_spin_lock_irqsave(&desc->lock, *flags); // raw spinlock get here
__irq_do_set_handler
mask_ack_irq
dwapb_irq_ack
spin_lock_irqsave(&gc->bgpio_lock, flags); // sleep able spinlock irq_put_desc_busunlock
Replace with a raw lock to avoid BUGs. This lock is only used to access registers, and It's safe to replace with the raw lock without bad influence.
[ 15.090359][ T1] =============================
[ 15.090365][ T1] [ BUG: Invalid wait context ]
[ 15.090373][ T1] 5.10.59-rt52-00983-g186a6841c682-dirty #3 Not tainted
[ 15.090386][ T1] -----------------------------
[ 15.090392][ T1] swapper/0/1 is trying to lock:
[ 15.090402][ T1] 70ff00018507c188 (&gc->bgpio_lock){....}-{3:3}, at: _raw_spin_lock_irqsave+0x1c/0x28
[ 15.090470][ T1] other info that might help us debug this:
[ 15.090477][ T1] context-{5:5}
[ 15.090485][ T1] 3 locks held by swapper/0/1:
[ 15.090497][ T1] #0: c2ff0001816de1a0 (&dev->mutex){....}-{4:4}, at: __device_driver_lock+0x98/0x104
[ 15.090553][ T1] #1: ffff90001485b4b8 (irq_domain_mutex){+.+.}-{4:4}, at: irq_domain_associate+0xbc/0x6d4
[ 15.090606][ T1] #2: 4bff000185d7a8e0 (lock_class){....}-{2:2}, at: _raw_spin_lock_irqsave+0x1c/0x28
[ 15.090654][ T1] stack backtrace:
[ 15.090661][ T1] CPU: 4 PID: 1 Comm: swapper/0 Not tainted 5.10.59-rt52-00983-g186a6841c682-dirty #3
[ 15.090682][ T1] Hardware name: Horizon Robotics Journey 5 DVB (DT)
[ 15.090692][ T1] Call trace:
......
[ 15.090811][ T1] _raw_spin_lock_irqsave+0x1c/0x28
[ 15.090828][ T1] dwapb_irq_ack+0xb4/0x300
[ 15.090846][ T1] __irq_do_set_handler+0x494/0xb2c
[ 15.090864][ T1] __irq_set_handler+0x74/0x114
[ 15.090881][ T1] irq_set_chip_and_handler_name+0x44/0x58
[ 15.090900][ T1] gpiochip_irq_map+0x210/0x644Stable-dep-of: e5464277625c ("gpio: mxc: Protect GPIO irqchip RMW with bgpio spinlock")
--- drivers/gpio/gpio-amdpt.c | 10 +++---- drivers/gpio/gpio-brcmstb.c | 12 ++++---- drivers/gpio/gpio-cadence.c | 12 ++++---- drivers/gpio/gpio-dwapb.c | 36 +++++++++++------------ drivers/gpio/gpio-grgpio.c | 30 +++++++++---------- drivers/gpio/gpio-hlwd.c | 18 ++++++------ drivers/gpio/gpio-idt3243x.c | 12 ++++---- drivers/gpio/gpio-ixp4xx.c | 4 +-- drivers/gpio/gpio-loongson1.c | 8 ++--- drivers/gpio/gpio-menz127.c | 8 ++--- drivers/gpio/gpio-mlxbf2.c | 6 ++-- drivers/gpio/gpio-mmio.c | 22 +++++++------- drivers/gpio/gpio-sifive.c | 12 ++++---- drivers/gpio/gpio-tb10x.c | 4 +-- drivers/pinctrl/nuvoton/pinctrl-npcm7xx.c | 8 ++--- include/linux/gpio/driver.h | 2 +- 16 files changed, 102 insertions(+), 102 deletions(-)
drivers/gpio/gpio-amdpt.c +5 -5
@@ -35,19 +35,19 @@ static int pt_gpio_request(struct gpio_chip *gc, unsigned offset)dev_dbg (gc->parent,"pt_gpio_request offset=%x\n" , offset); -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); using_pins =readl (pt_gpio->reg_base +PT_SYNC_REG );if (using_pins &BIT (offset)) {dev_warn (gc->parent,"PT GPIO pin %x reconfigured\n" , offset); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return -EINVAL ; }writel (using_pins |BIT (offset), pt_gpio->reg_base +PT_SYNC_REG ); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
@@ -58,13 +58,13 @@ static void pt_gpio_free(struct gpio_chip *gc, unsigned offset)unsigned long flags;u32 using_pins; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); using_pins =readl (pt_gpio->reg_base +PT_SYNC_REG ); using_pins &= ~BIT (offset);writel (using_pins, pt_gpio->reg_base +PT_SYNC_REG ); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);dev_dbg (gc->parent,"pt_gpio_free offset=%x\n" , offset); }
drivers/gpio/gpio-brcmstb.c +6 -6
@@ -92,9 +92,9 @@ brcmstb_gpio_get_active_irqs(struct brcmstb_gpio_bank *bank)unsigned long status;unsigned long flags; -spin_lock_irqsave (&bank->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&bank->gc.bgpio_lock, flags); status =__brcmstb_gpio_get_active_irqs (bank); -spin_unlock_irqrestore (&bank->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&bank->gc.bgpio_lock, flags);return status; }
@@ -114,14 +114,14 @@ static void brcmstb_gpio_set_imask(struct brcmstb_gpio_bank *bank,u32 imask;unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); imask = gc->read_reg (priv->reg_base +GIO_MASK (bank->id));if (enable) imask |= mask;else imask &= ~mask; gc->write_reg (priv->reg_base +GIO_MASK (bank->id), imask); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static int brcmstb_gpio_to_irq (struct gpio_chip *gc,unsigned offset)
@@ -204,7 +204,7 @@ static int brcmstb_gpio_irq_set_type(struct irq_data *d, unsigned int type)return -EINVAL ; } -spin_lock_irqsave (&bank->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&bank->gc.bgpio_lock, flags); iedge_config = bank->gc.read_reg (priv->reg_base +GIO_EC (bank->id)) & ~mask;
@@ -220,7 +220,7 @@ static int brcmstb_gpio_irq_set_type(struct irq_data *d, unsigned int type) bank->gc.write_reg (priv->reg_base +GIO_LEVEL (bank->id), ilevel | level); -spin_unlock_irqrestore (&bank->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&bank->gc.bgpio_lock, flags);return 0 ; }
drivers/gpio/gpio-cadence.c +6 -6
@@ -41,12 +41,12 @@ static int cdns_gpio_request(struct gpio_chip *chip, unsigned int offset)struct cdns_gpio_chip *cgpio =gpiochip_get_data (chip);unsigned long flags; -spin_lock_irqsave (&chip->bgpio_lock, flags); +raw_spin_lock_irqsave (&chip->bgpio_lock, flags);iowrite32 (ioread32 (cgpio->regs +CDNS_GPIO_BYPASS_MODE ) & ~BIT (offset), cgpio->regs +CDNS_GPIO_BYPASS_MODE ); -spin_unlock_irqrestore (&chip->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&chip->bgpio_lock, flags);return 0 ; }
@@ -55,13 +55,13 @@ static void cdns_gpio_free(struct gpio_chip *chip, unsigned int offset)struct cdns_gpio_chip *cgpio =gpiochip_get_data (chip);unsigned long flags; -spin_lock_irqsave (&chip->bgpio_lock, flags); +raw_spin_lock_irqsave (&chip->bgpio_lock, flags);iowrite32 (ioread32 (cgpio->regs +CDNS_GPIO_BYPASS_MODE ) | (BIT (offset) & cgpio->bypass_orig), cgpio->regs +CDNS_GPIO_BYPASS_MODE ); -spin_unlock_irqrestore (&chip->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&chip->bgpio_lock, flags); }static void cdns_gpio_irq_mask (struct irq_data *d)
@@ -90,7 +90,7 @@ static int cdns_gpio_irq_set_type(struct irq_data *d, unsigned int type)u32 mask =BIT (d->hwirq);int ret =0 ; -spin_lock_irqsave (&chip->bgpio_lock, flags); +raw_spin_lock_irqsave (&chip->bgpio_lock, flags); int_value =ioread32 (cgpio->regs +CDNS_GPIO_IRQ_VALUE ) & ~mask; int_type =ioread32 (cgpio->regs +CDNS_GPIO_IRQ_TYPE ) & ~mask;
@@ -115,7 +115,7 @@ static int cdns_gpio_irq_set_type(struct irq_data *d, unsigned int type)iowrite32 (int_type, cgpio->regs +CDNS_GPIO_IRQ_TYPE ); err_irq_type: -spin_unlock_irqrestore (&chip->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&chip->bgpio_lock, flags);return ret; }
drivers/gpio/gpio-dwapb.c +18 -18
@@ -242,9 +242,9 @@ static void dwapb_irq_ack(struct irq_data *d)u32 val =BIT (irqd_to_hwirq (d));unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);dwapb_write (gpio,GPIO_PORTA_EOI , val); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static void dwapb_irq_mask (struct irq_data *d)
@@ -254,10 +254,10 @@ static void dwapb_irq_mask(struct irq_data *d)unsigned long flags;u32 val; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val =dwapb_read (gpio,GPIO_INTMASK ) |BIT (irqd_to_hwirq (d));dwapb_write (gpio,GPIO_INTMASK , val); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static void dwapb_irq_unmask (struct irq_data *d)
@@ -267,10 +267,10 @@ static void dwapb_irq_unmask(struct irq_data *d)unsigned long flags;u32 val; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val =dwapb_read (gpio,GPIO_INTMASK ) & ~BIT (irqd_to_hwirq (d));dwapb_write (gpio,GPIO_INTMASK , val); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static void dwapb_irq_enable (struct irq_data *d)
@@ -280,11 +280,11 @@ static void dwapb_irq_enable(struct irq_data *d)unsigned long flags;u32 val; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val =dwapb_read (gpio,GPIO_INTEN ); val |=BIT (irqd_to_hwirq (d));dwapb_write (gpio,GPIO_INTEN , val); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static void dwapb_irq_disable (struct irq_data *d)
@@ -294,11 +294,11 @@ static void dwapb_irq_disable(struct irq_data *d)unsigned long flags;u32 val; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val =dwapb_read (gpio,GPIO_INTEN ); val &= ~BIT (irqd_to_hwirq (d));dwapb_write (gpio,GPIO_INTEN , val); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static int dwapb_irq_set_type (struct irq_data *d,u32 type)
@@ -308,7 +308,7 @@ static int dwapb_irq_set_type(struct irq_data *d, u32 type)irq_hw_number_t bit =irqd_to_hwirq (d);unsigned long level, polarity, flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); level =dwapb_read (gpio,GPIO_INTTYPE_LEVEL ); polarity =dwapb_read (gpio,GPIO_INT_POLARITY );
@@ -343,7 +343,7 @@ static int dwapb_irq_set_type(struct irq_data *d, u32 type)dwapb_write (gpio,GPIO_INTTYPE_LEVEL , level);if (type !=IRQ_TYPE_EDGE_BOTH )dwapb_write (gpio,GPIO_INT_POLARITY , polarity); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
@@ -373,7 +373,7 @@ static int dwapb_gpio_set_debounce(struct gpio_chip *gc,unsigned long flags, val_deb;unsigned long mask =BIT (offset); -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val_deb =dwapb_read (gpio,GPIO_PORTA_DEBOUNCE );if (debounce)
@@ -382,7 +382,7 @@ static int dwapb_gpio_set_debounce(struct gpio_chip *gc, val_deb &= ~mask;dwapb_write (gpio,GPIO_PORTA_DEBOUNCE , val_deb); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
@@ -738,7 +738,7 @@ static int dwapb_gpio_suspend(struct device *dev)unsigned long flags;int i; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);for (i =0 ; i < gpio->nr_ports; i++) {unsigned int offset;unsigned int idx = gpio->ports[i].idx;
@@ -765,7 +765,7 @@ static int dwapb_gpio_suspend(struct device *dev)dwapb_write (gpio,GPIO_INTMASK , ~ctx->wake_en); } } -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);clk_bulk_disable_unprepare (DWAPB_NR_CLOCKS , gpio->clks);
@@ -785,7 +785,7 @@ static int dwapb_gpio_resume(struct device *dev)return err; } -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);for (i =0 ; i < gpio->nr_ports; i++) {unsigned int offset;unsigned int idx = gpio->ports[i].idx;
@@ -812,7 +812,7 @@ static int dwapb_gpio_resume(struct device *dev)dwapb_write (gpio,GPIO_PORTA_EOI ,0xffffffff ); } } -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
drivers/gpio/gpio-grgpio.c +15 -15
@@ -145,7 +145,7 @@ static int grgpio_irq_set_type(struct irq_data *d, unsigned int type)return -EINVAL ; } -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags); ipol = priv->gc.read_reg (priv->regs +GRGPIO_IPOL ) & ~mask; iedge = priv->gc.read_reg (priv->regs +GRGPIO_IEDGE ) & ~mask;
@@ -153,7 +153,7 @@ static int grgpio_irq_set_type(struct irq_data *d, unsigned int type) priv->gc.write_reg (priv->regs +GRGPIO_IPOL , ipol | pol); priv->gc.write_reg (priv->regs +GRGPIO_IEDGE , iedge | edge); -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags);return 0 ; }
@@ -164,11 +164,11 @@ static void grgpio_irq_mask(struct irq_data *d)int offset = d->hwirq;unsigned long flags; -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags);grgpio_set_imask (priv, offset,0 ); -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); }static void grgpio_irq_unmask (struct irq_data *d)
@@ -177,11 +177,11 @@ static void grgpio_irq_unmask(struct irq_data *d)int offset = d->hwirq;unsigned long flags; -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags);grgpio_set_imask (priv, offset,1 ); -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); }static struct irq_chip grgpio_irq_chip = {
@@ -199,7 +199,7 @@ static irqreturn_t grgpio_irq_handler(int irq, void *dev)int i;int match =0 ; -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags);/* * For each gpio line, call its interrupt handler if it its underlying
@@ -215,7 +215,7 @@ static irqreturn_t grgpio_irq_handler(int irq, void *dev) } } -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags);if (!match)dev_warn (priv->dev,"No gpio line matched irq %d\n" , irq);
@@ -247,13 +247,13 @@ static int grgpio_irq_map(struct irq_domain *d, unsigned int irq,dev_dbg (priv->dev,"Mapping irq %d for gpio line %d\n" , irq, offset); -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags);/* Request underlying irq if not already requested */ lirq->irq = irq; uirq = &priv->uirqs[lirq->index];if (uirq->refcnt ==0 ) { -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); ret =request_irq (uirq->uirq, grgpio_irq_handler,0 ,dev_name (priv->dev), priv);if (ret) {
@@ -262,11 +262,11 @@ static int grgpio_irq_map(struct irq_domain *d, unsigned int irq, uirq->uirq);return ret; } -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags); } uirq->refcnt++; -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags);/* Setup irq */ irq_set_chip_data (irq, priv);
@@ -290,7 +290,7 @@ static void grgpio_irq_unmap(struct irq_domain *d, unsigned int irq)irq_set_chip_and_handler (irq,NULL ,NULL );irq_set_chip_data (irq,NULL ); -spin_lock_irqsave (&priv->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&priv->gc.bgpio_lock, flags);/* Free underlying irq if last user unmapped */ index =-1 ;
@@ -309,13 +309,13 @@ static void grgpio_irq_unmap(struct irq_domain *d, unsigned int irq) uirq = &priv->uirqs[lirq->index]; uirq->refcnt--;if (uirq->refcnt ==0 ) { -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags);free_irq (uirq->uirq, priv);return ; } } -spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&priv->gc.bgpio_lock, flags); }static const struct irq_domain_ops grgpio_irq_domain_ops = {
drivers/gpio/gpio-hlwd.c +9 -9
@@ -65,7 +65,7 @@ static void hlwd_gpio_irqhandler(struct irq_desc *desc)int hwirq;u32 emulated_pending; -spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); pending =ioread32be (hlwd->regs +HW_GPIOB_INTFLAG ); pending &=ioread32be (hlwd->regs +HW_GPIOB_INTMASK );
@@ -93,7 +93,7 @@ static void hlwd_gpio_irqhandler(struct irq_desc *desc)/* Mark emulated interrupts as pending */ pending |= rising | falling; } -spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags);chained_irq_enter (chip, desc);
@@ -118,11 +118,11 @@ static void hlwd_gpio_irq_mask(struct irq_data *data)unsigned long flags;u32 mask; -spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); mask =ioread32be (hlwd->regs +HW_GPIOB_INTMASK ); mask &= ~BIT (data->hwirq);iowrite32be (mask, hlwd->regs +HW_GPIOB_INTMASK ); -spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); }static void hlwd_gpio_irq_unmask (struct irq_data *data)
@@ -132,11 +132,11 @@ static void hlwd_gpio_irq_unmask(struct irq_data *data)unsigned long flags;u32 mask; -spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); mask =ioread32be (hlwd->regs +HW_GPIOB_INTMASK ); mask |=BIT (data->hwirq);iowrite32be (mask, hlwd->regs +HW_GPIOB_INTMASK ); -spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); }static void hlwd_gpio_irq_enable (struct irq_data *data)
@@ -173,7 +173,7 @@ static int hlwd_gpio_irq_set_type(struct irq_data *data, unsigned int flow_type)unsigned long flags;u32 level; -spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_lock_irqsave (&hlwd->gpioc.bgpio_lock, flags); hlwd->edge_emulation &= ~BIT (data->hwirq);
@@ -194,11 +194,11 @@ static int hlwd_gpio_irq_set_type(struct irq_data *data, unsigned int flow_type)hlwd_gpio_irq_setup_emulation (hlwd, data->hwirq, flow_type);break ;default : -spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags);return -EINVAL ; } -spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&hlwd->gpioc.bgpio_lock, flags);return 0 ; }
drivers/gpio/gpio-idt3243x.c +6 -6
@@ -57,7 +57,7 @@ static int idt_gpio_irq_set_type(struct irq_data *d, unsigned int flow_type)if (sense ==IRQ_TYPE_NONE || (sense &IRQ_TYPE_EDGE_BOTH ))return -EINVAL ; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); ilevel =readl (ctrl->gpio +IDT_GPIO_ILEVEL );if (sense &IRQ_TYPE_LEVEL_HIGH )
@@ -68,7 +68,7 @@ static int idt_gpio_irq_set_type(struct irq_data *d, unsigned int flow_type)writel (ilevel, ctrl->gpio +IDT_GPIO_ILEVEL );irq_set_handler_locked (d, handle_level_irq); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
@@ -86,12 +86,12 @@ static void idt_gpio_mask(struct irq_data *d)struct idt_gpio_ctrl *ctrl =gpiochip_get_data (gc);unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); ctrl->mask_cache |=BIT (d->hwirq);writel (ctrl->mask_cache, ctrl->pic +IDT_PIC_IRQ_MASK ); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static void idt_gpio_unmask (struct irq_data *d)
@@ -100,12 +100,12 @@ static void idt_gpio_unmask(struct irq_data *d)struct idt_gpio_ctrl *ctrl =gpiochip_get_data (gc);unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); ctrl->mask_cache &= ~BIT (d->hwirq);writel (ctrl->mask_cache, ctrl->pic +IDT_PIC_IRQ_MASK ); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static int idt_gpio_irq_init_hw (struct gpio_chip *gc)
drivers/gpio/gpio-ixp4xx.c +2 -2
@@ -128,7 +128,7 @@ static int ixp4xx_gpio_irq_set_type(struct irq_data *d, unsigned int type) int_reg =IXP4XX_REG_GPIT1 ; } -spin_lock_irqsave (&g->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&g->gc.bgpio_lock, flags);/* Clear the style for the appropriate pin */ val =__raw_readl (g->base + int_reg);
@@ -147,7 +147,7 @@ static int ixp4xx_gpio_irq_set_type(struct irq_data *d, unsigned int type) val |=BIT (d->hwirq);__raw_writel (val, g->base +IXP4XX_REG_GPOE ); -spin_unlock_irqrestore (&g->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&g->gc.bgpio_lock, flags);/* This parent only accept level high (asserted) */ return irq_chip_set_type_parent (d,IRQ_TYPE_LEVEL_HIGH );
drivers/gpio/gpio-loongson1.c +4 -4
@@ -25,10 +25,10 @@ static int ls1x_gpio_request(struct gpio_chip *gc, unsigned int offset) {unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);__raw_writel (__raw_readl (gpio_reg_base +GPIO_CFG ) |BIT (offset), gpio_reg_base +GPIO_CFG ); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
@@ -37,10 +37,10 @@ static void ls1x_gpio_free(struct gpio_chip *gc, unsigned int offset) {unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);__raw_writel (__raw_readl (gpio_reg_base +GPIO_CFG ) & ~BIT (offset), gpio_reg_base +GPIO_CFG ); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static int ls1x_gpio_probe (struct platform_device *pdev)
drivers/gpio/gpio-menz127.c +4 -4
@@ -64,7 +64,7 @@ static int men_z127_debounce(struct gpio_chip *gc, unsigned gpio, debounce /=50 ; } -spin_lock (&gc->bgpio_lock); +raw_spin_lock (&gc->bgpio_lock); db_en =readl (priv->reg_base +MEN_Z127_DBER );
@@ -79,7 +79,7 @@ static int men_z127_debounce(struct gpio_chip *gc, unsigned gpio,writel (db_en, priv->reg_base +MEN_Z127_DBER );writel (db_cnt, priv->reg_base +GPIO_TO_DBCNT_REG (gpio)); -spin_unlock (&gc->bgpio_lock); +raw_spin_unlock (&gc->bgpio_lock);return 0 ; }
@@ -91,7 +91,7 @@ static int men_z127_set_single_ended(struct gpio_chip *gc,struct men_z127_gpio *priv =gpiochip_get_data (gc);u32 od_en; -spin_lock (&gc->bgpio_lock); +raw_spin_lock (&gc->bgpio_lock); od_en =readl (priv->reg_base +MEN_Z127_ODER );if (param ==PIN_CONFIG_DRIVE_OPEN_DRAIN )
@@ -101,7 +101,7 @@ static int men_z127_set_single_ended(struct gpio_chip *gc, od_en &= ~BIT (offset);writel (od_en, priv->reg_base +MEN_Z127_ODER ); -spin_unlock (&gc->bgpio_lock); +raw_spin_unlock (&gc->bgpio_lock);return 0 ; }
drivers/gpio/gpio-mlxbf2.c +3 -3
@@ -120,7 +120,7 @@ static int mlxbf2_gpio_lock_acquire(struct mlxbf2_gpio_context *gs)u32 arm_gpio_lock_val;mutex_lock (yu_arm_gpio_lock_param.lock); -spin_lock (&gs->gc.bgpio_lock); +raw_spin_lock (&gs->gc.bgpio_lock); arm_gpio_lock_val =readl (yu_arm_gpio_lock_param.io);
@@ -128,7 +128,7 @@ static int mlxbf2_gpio_lock_acquire(struct mlxbf2_gpio_context *gs)* When lock active bit[31] is set, ModeX is write enabled */ if (YU_LOCK_ACTIVE_BIT (arm_gpio_lock_val)) { -spin_unlock (&gs->gc.bgpio_lock); +raw_spin_unlock (&gs->gc.bgpio_lock);mutex_unlock (yu_arm_gpio_lock_param.lock);return -EINVAL ; }
@@ -146,7 +146,7 @@ static void mlxbf2_gpio_lock_release(struct mlxbf2_gpio_context *gs) __releases(yu_arm_gpio_lock_param.lock) {writel (YU_ARM_GPIO_LOCK_RELEASE , yu_arm_gpio_lock_param.io); -spin_unlock (&gs->gc.bgpio_lock); +raw_spin_unlock (&gs->gc.bgpio_lock);mutex_unlock (yu_arm_gpio_lock_param.lock); }
drivers/gpio/gpio-mmio.c +11 -11
@@ -220,7 +220,7 @@ static void bgpio_set(struct gpio_chip *gc, unsigned int gpio, int val)unsigned long mask =bgpio_line2mask (gc, gpio);unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);if (val) gc->bgpio_data |= mask;
@@ -229,7 +229,7 @@ static void bgpio_set(struct gpio_chip *gc, unsigned int gpio, int val) gc->write_reg (gc->reg_dat, gc->bgpio_data); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); } static void bgpio_set_with_clear(struct gpio_chip *gc, unsigned int gpio,
@@ -248,7 +248,7 @@ static void bgpio_set_set(struct gpio_chip *gc, unsigned int gpio, int val)unsigned long mask =bgpio_line2mask (gc, gpio);unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);if (val) gc->bgpio_data |= mask;
@@ -257,7 +257,7 @@ static void bgpio_set_set(struct gpio_chip *gc, unsigned int gpio, int val) gc->write_reg (gc->reg_set, gc->bgpio_data); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); } static void bgpio_multiple_get_masks(struct gpio_chip *gc,
@@ -286,7 +286,7 @@ static void bgpio_set_multiple_single_reg(struct gpio_chip *gc,unsigned long flags;unsigned long set_mask, clear_mask; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);bgpio_multiple_get_masks (gc, mask, bits, &set_mask, &clear_mask);
@@ -295,7 +295,7 @@ static void bgpio_set_multiple_single_reg(struct gpio_chip *gc, gc->write_reg (reg, gc->bgpio_data); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); } static void bgpio_set_multiple(struct gpio_chip *gc, unsigned long *mask,
@@ -347,7 +347,7 @@ static int bgpio_dir_in(struct gpio_chip *gc, unsigned int gpio) {unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); gc->bgpio_dir &= ~bgpio_line2mask (gc, gpio);
@@ -356,7 +356,7 @@ static int bgpio_dir_in(struct gpio_chip *gc, unsigned int gpio)if (gc->reg_dir_out) gc->write_reg (gc->reg_dir_out, gc->bgpio_dir); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);return 0 ; }
@@ -387,7 +387,7 @@ static void bgpio_dir_out(struct gpio_chip *gc, unsigned int gpio, int val) {unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); gc->bgpio_dir |=bgpio_line2mask (gc, gpio);
@@ -396,7 +396,7 @@ static void bgpio_dir_out(struct gpio_chip *gc, unsigned int gpio, int val)if (gc->reg_dir_out) gc->write_reg (gc->reg_dir_out, gc->bgpio_dir); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); } static int bgpio_dir_out_dir_first(struct gpio_chip *gc, unsigned int gpio,
@@ -610,7 +610,7 @@ int bgpio_init(struct gpio_chip *gc, struct device *dev,if (gc->bgpio_bits >BITS_PER_LONG )return -EINVAL ; -spin_lock_init (&gc->bgpio_lock); +raw_spin_lock_init (&gc->bgpio_lock); gc->parent = dev; gc->label =dev_name (dev); gc->base =-1 ;
drivers/gpio/gpio-sifive.c +6 -6
@@ -44,7 +44,7 @@ static void sifive_gpio_set_ie(struct sifive_gpio *chip, unsigned int offset)unsigned long flags;unsigned int trigger; -spin_lock_irqsave (&chip->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&chip->gc.bgpio_lock, flags); trigger = (chip->irq_state &BIT (offset)) ? chip->trigger[offset] :0 ;regmap_update_bits (chip->regs,SIFIVE_GPIO_RISE_IE ,BIT (offset), (trigger &IRQ_TYPE_EDGE_RISING ) ?BIT (offset) :0 );
@@ -54,7 +54,7 @@ static void sifive_gpio_set_ie(struct sifive_gpio *chip, unsigned int offset) (trigger & IRQ_TYPE_LEVEL_HIGH) ? BIT(offset) : 0);regmap_update_bits (chip->regs,SIFIVE_GPIO_LOW_IE ,BIT (offset), (trigger &IRQ_TYPE_LEVEL_LOW ) ?BIT (offset) :0 ); -spin_unlock_irqrestore (&chip->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&chip->gc.bgpio_lock, flags); }static int sifive_gpio_irq_set_type (struct irq_data *d,unsigned int trigger)
@@ -84,13 +84,13 @@ static void sifive_gpio_irq_enable(struct irq_data *d)/* Switch to input */ gc->direction_input (gc, offset); -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);/* Clear any sticky pending interrupts */ regmap_write (chip->regs,SIFIVE_GPIO_RISE_IP , bit);regmap_write (chip->regs,SIFIVE_GPIO_FALL_IP , bit);regmap_write (chip->regs,SIFIVE_GPIO_HIGH_IP , bit);regmap_write (chip->regs,SIFIVE_GPIO_LOW_IP , bit); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);/* Enable interrupts */ assign_bit (offset, &chip->irq_state,1 );
@@ -116,13 +116,13 @@ static void sifive_gpio_irq_eoi(struct irq_data *d)u32 bit =BIT (offset);unsigned long flags; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags);/* Clear all pending interrupts */ regmap_write (chip->regs,SIFIVE_GPIO_RISE_IP , bit);regmap_write (chip->regs,SIFIVE_GPIO_FALL_IP , bit);regmap_write (chip->regs,SIFIVE_GPIO_HIGH_IP , bit);regmap_write (chip->regs,SIFIVE_GPIO_LOW_IP , bit); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags);irq_chip_eoi_parent (d); }
drivers/gpio/gpio-tb10x.c +2 -2
@@ -62,14 +62,14 @@ static inline void tb10x_set_bits(struct tb10x_gpio *gpio, unsigned int offs,u32 r;unsigned long flags; -spin_lock_irqsave (&gpio->gc.bgpio_lock, flags); +raw_spin_lock_irqsave (&gpio->gc.bgpio_lock, flags); r =tb10x_reg_read (gpio, offs); r = (r & ~mask) | (val & mask);tb10x_reg_write (gpio, offs, r); -spin_unlock_irqrestore (&gpio->gc.bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gpio->gc.bgpio_lock, flags); }static int tb10x_gpio_to_irq (struct gpio_chip *chip,unsigned offset)
drivers/pinctrl/nuvoton/pinctrl-npcm7xx.c +4 -4
@@ -104,12 +104,12 @@ static void npcm_gpio_set(struct gpio_chip *gc, void __iomem *reg,unsigned long flags;unsigned long val; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val =ioread32 (reg) | pinmask;iowrite32 (val, reg); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); } static void npcm_gpio_clr(struct gpio_chip *gc, void __iomem *reg,
@@ -118,12 +118,12 @@ static void npcm_gpio_clr(struct gpio_chip *gc, void __iomem *reg,unsigned long flags;unsigned long val; -spin_lock_irqsave (&gc->bgpio_lock, flags); +raw_spin_lock_irqsave (&gc->bgpio_lock, flags); val =ioread32 (reg) & ~pinmask;iowrite32 (val, reg); -spin_unlock_irqrestore (&gc->bgpio_lock, flags); +raw_spin_unlock_irqrestore (&gc->bgpio_lock, flags); }static void npcmgpio_dbg_show (struct seq_file *s,struct gpio_chip *chip)
include/linux/gpio/driver.h +1 -1
@@ -425,7 +425,7 @@ struct gpio_chip {void __iomem *reg_dir_in;bool bgpio_dir_unreadable;int bgpio_bits; -spinlock_t bgpio_lock; +raw_spinlock_t bgpio_lock;unsigned long bgpio_data;unsigned long bgpio_dir;#endif /* CONFIG_GPIO_GENERIC */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 43/204 gpio: mxc: Protect GPIO irqchip RMW with bgpio spinlock
In reply to Greg Kroah-HartmanFrom: Marek Vasut <[email protected]>
[ Upstream commit e5464277625c1aca5c002e0f470377cdd6816dcf ]
The driver currently performs register read-modify-write without locking in its irqchip part, this could lead to a race condition when configuring interrupt mode setting. Add the missing bgpio spinlock lock/unlock around the register read-modify-write.
--- drivers/gpio/gpio-mxc.c | 11 +++++++++++ 1 file changed, 11 insertions(+)
drivers/gpio/gpio-mxc.c +11 -0
@@ -18,6 +18,7 @@#include <linux/module.h> #include <linux/platform_device.h> #include <linux/slab.h> +#include <linux/spinlock.h> #include <linux/syscore_ops.h> #include <linux/gpio/driver.h> #include <linux/of.h>
@@ -147,6 +148,7 @@ static int gpio_set_irq_type(struct irq_data *d, u32 type) {struct irq_chip_generic *gc =irq_data_get_irq_chip_data (d);struct mxc_gpio_port *port = gc->private; +unsigned long flags;u32 bit, val;u32 gpio_idx = d->hwirq;int edge;
@@ -185,6 +187,8 @@ static int gpio_set_irq_type(struct irq_data *d, u32 type)return -EINVAL ; } +raw_spin_lock_irqsave (&port->gc.bgpio_lock, flags); +if (GPIO_EDGE_SEL >=0 ) { val =readl (port->base +GPIO_EDGE_SEL );if (edge ==GPIO_INT_BOTH_EDGES )
@@ -204,15 +208,20 @@ static int gpio_set_irq_type(struct irq_data *d, u32 type)writel (1 << gpio_idx, port->base +GPIO_ISR ); +raw_spin_unlock_irqrestore (&port->gc.bgpio_lock, flags); +return 0 ; }static void mxc_flip_edge (struct mxc_gpio_port *port,u32 gpio) {void __iomem *reg = port->base; +unsigned long flags;u32 bit, val;int edge; +raw_spin_lock_irqsave (&port->gc.bgpio_lock, flags); + reg +=GPIO_ICR1 + ((gpio &0x10 ) >>2 );/* lower or upper register */ bit = gpio &0xf ; val =readl (reg);
@@ -230,6 +239,8 @@ static void mxc_flip_edge(struct mxc_gpio_port *port, u32 gpio)return ; }writel (val | (edge << (bit <<1 )), reg); + +raw_spin_unlock_irqrestore (&port->gc.bgpio_lock, flags); }/* handle 32 interrupts in one status register */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 44/204 gpio: mxc: Always set GPIOs used as interrupt source to INPUT mode
In reply to Greg Kroah-HartmanFrom: Marek Vasut <[email protected]>
[ Upstream commit 8e88a0feebb241cab0253698b2f7358b6ebec802 ]
Always configure GPIO pins which are used as interrupt source as INPUTs. In case the default pin configuration is OUTPUT, or the prior stage does configure the pins as OUTPUT, then Linux will not reconfigure the pin as INPUT and no interrupts are received.
Always configure the interrupt source GPIO pin as input to fix the above case.
--- drivers/gpio/gpio-mxc.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/gpio/gpio-mxc.c +1 -1
@@ -210,7 +210,7 @@ static int gpio_set_irq_type(struct irq_data *d, u32 type)raw_spin_unlock_irqrestore (&port->gc.bgpio_lock, flags); -return 0 ; +return port->gc.direction_input (&port->gc, gpio_idx); }static void mxc_flip_edge (struct mxc_gpio_port *port,u32 gpio)
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 45/204 wifi: rndis_wlan: Prevent buffer overflow in rndis_query_oid
In reply to Greg Kroah-HartmanFrom: Szymon Heidrich <[email protected]>
[ Upstream commit b870e73a56c4cccbec33224233eaf295839f228c ]
Since resplen and respoffs are signed integers sufficiently large values of unsigned int len and offset members of RNDIS response will result in negative values of prior variables. This may be utilized to bypass implemented security checks to either extract memory contents by manipulating offset or overflow the data buffer via memcpy by manipulating both offset and len.
Additionally assure that sum of resplen and respoffs does not overflow so buffer boundaries are kept.
--- drivers/net/wireless/rndis_wlan.c | 19 ++++++------------- 1 file changed, 6 insertions(+), 13 deletions(-)
drivers/net/wireless/rndis_wlan.c +6 -13
@@ -694,8 +694,8 @@ static int rndis_query_oid(struct usbnet *dev, u32 oid, void *data, int *len)struct rndis_query *get;struct rndis_query_c *get_c; } u; -int ret, buflen; -int resplen, respoffs, copylen; +int ret; +size_t buflen, resplen, respoffs, copylen; buflen = *len +sizeof (*u.get);if (buflen <CONTROL_BUFFER_SIZE )
@@ -730,22 +730,15 @@ static int rndis_query_oid(struct usbnet *dev, u32 oid, void *data, int *len)if (respoffs > buflen) {/* Device returned data offset outside buffer, error. */ -netdev_dbg (dev->net,"%s(%s): received invalid " -"data offset: %d > %d\n" , __func__, -oid_to_string (oid), respoffs, buflen); +netdev_dbg (dev->net, +"%s(%s): received invalid data offset: %zu > %zu\n" , + __func__,oid_to_string (oid), respoffs, buflen); ret = -EINVAL ; goto exit_unlock; } -if ((resplen + respoffs) > buflen) { -/* Device would have returned more data if buffer would -* have been big enough. Copy just the bits that we got. -*/ - copylen = buflen - respoffs; - }else { - copylen = resplen; - } + copylen =min (resplen, buflen - respoffs);if (copylen > *len) copylen = *len;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 46/204 pinctrl/rockchip: Use temporary variable for struct device
In reply to Greg Kroah-HartmanFrom: Andy Shevchenko <[email protected]>
[ Upstream commit e4dd7fd5ff0acb3f3ed290f52afe20fd840d22b0 ]
Use temporary variable for struct device to make code neater.
Stable-dep-of: 31b62a98de42 ("pinctrl: rockchip: fix reading pull type on rk3568")
--- drivers/pinctrl/pinctrl-rockchip.c | 116 +++++++++++++---------------- 1 file changed, 53 insertions(+), 63 deletions(-)
drivers/pinctrl/pinctrl-rockchip.c +53 -63
@@ -285,6 +285,7 @@ static int rockchip_dt_node_to_map(struct pinctrl_dev *pctldev, {struct rockchip_pinctrl *info =pinctrl_dev_get_drvdata (pctldev);const struct rockchip_pin_group *grp; +struct device *dev = info->dev;struct pinctrl_map *new_map;struct device_node *parent;int map_num =1 ;
@@ -296,8 +297,7 @@ static int rockchip_dt_node_to_map(struct pinctrl_dev *pctldev,*/ grp =pinctrl_name_to_group (info, np->name);if (!grp) { -dev_err (info->dev,"unable to find group for node %pOFn\n" , - np); +dev_err (dev,"unable to find group for node %pOFn\n" , np);return -EINVAL ; }
@@ -331,7 +331,7 @@ static int rockchip_dt_node_to_map(struct pinctrl_dev *pctldev, new_map[i].data.configs.num_configs = grp->data[i].nconfigs; } -dev_dbg (pctldev->dev,"maps: function %s group %s num %d\n" , +dev_dbg (dev,"maps: function %s group %s num %d\n" , (*map)->data.mux.function, (*map)->data.mux.group, map_num);return 0 ;
@@ -927,20 +927,20 @@ static int rockchip_verify_mux(struct rockchip_pin_bank *bank, int pin, int mux) {struct rockchip_pinctrl *info = bank->drvdata; +struct device *dev = info->dev;int iomux_num = (pin /8 );if (iomux_num >3 )return -EINVAL ;if (bank->iomux[iomux_num].type &IOMUX_UNROUTED ) { -dev_err (info->dev,"pin %d is unrouted\n" , pin); +dev_err (dev,"pin %d is unrouted\n" , pin);return -EINVAL ; }if (bank->iomux[iomux_num].type &IOMUX_GPIO_ONLY ) {if (mux !=RK_FUNC_GPIO ) { -dev_err (info->dev, -"pin %d only supports a gpio mux\n" , pin); +dev_err (dev,"pin %d only supports a gpio mux\n" , pin);return -ENOTSUPP ; } }
@@ -964,6 +964,7 @@ static int rockchip_verify_mux(struct rockchip_pin_bank *bank,static int rockchip_set_mux (struct rockchip_pin_bank *bank,int pin,int mux) {struct rockchip_pinctrl *info = bank->drvdata; +struct device *dev = info->dev;int iomux_num = (pin /8 );struct regmap *regmap;int reg, ret, mask, mux_type;
@@ -977,8 +978,7 @@ static int rockchip_set_mux(struct rockchip_pin_bank *bank, int pin, int mux)if (bank->iomux[iomux_num].type &IOMUX_GPIO_ONLY )return 0 ; -dev_dbg (info->dev,"setting mux of GPIO%d-%d to %d\n" , - bank->bank_num, pin, mux); +dev_dbg (dev,"setting mux of GPIO%d-%d to %d\n" , bank->bank_num, pin, mux); regmap = (bank->iomux[iomux_num].type &IOMUX_SOURCE_PMU ) ? info->regmap_pmu : info->regmap_base;
@@ -1630,6 +1630,7 @@ static int rockchip_get_drive_perpin(struct rockchip_pin_bank *bank, {struct rockchip_pinctrl *info = bank->drvdata;struct rockchip_pin_ctrl *ctrl = info->ctrl; +struct device *dev = info->dev;struct regmap *regmap;int reg, ret;u32 data, temp, rmask_bits;
@@ -1675,7 +1676,7 @@ static int rockchip_get_drive_perpin(struct rockchip_pin_bank *bank, bit -=16 ;break ;default : -dev_err (info->dev,"unsupported bit: %d for pinctrl drive type: %d\n" , +dev_err (dev,"unsupported bit: %d for pinctrl drive type: %d\n" , bit, drv_type);return -EINVAL ; }
@@ -1687,8 +1688,7 @@ static int rockchip_get_drive_perpin(struct rockchip_pin_bank *bank, rmask_bits =RK3288_DRV_BITS_PER_PIN ;break ;default : -dev_err (info->dev,"unsupported pinctrl drive type: %d\n" , - drv_type); +dev_err (dev,"unsupported pinctrl drive type: %d\n" , drv_type);return -EINVAL ; }
@@ -1707,13 +1707,14 @@ static int rockchip_set_drive_perpin(struct rockchip_pin_bank *bank, {struct rockchip_pinctrl *info = bank->drvdata;struct rockchip_pin_ctrl *ctrl = info->ctrl; +struct device *dev = info->dev;struct regmap *regmap;int reg, ret, i;u32 data, rmask, rmask_bits, temp;u8 bit;int drv_type = bank->drv[pin_num /8 ].drv_type; -dev_dbg (info->dev,"setting drive of GPIO%d-%d to %d\n" , +dev_dbg (dev,"setting drive of GPIO%d-%d to %d\n" , bank->bank_num, pin_num, strength); ctrl->drv_calc_reg (bank, pin_num, ®map, ®, &bit);
@@ -1735,8 +1736,7 @@ static int rockchip_set_drive_perpin(struct rockchip_pin_bank *bank, }if (ret <0 ) { -dev_err (info->dev,"unsupported driver strength %d\n" , - strength); +dev_err (dev,"unsupported driver strength %d\n" , strength);return ret; }
@@ -1775,7 +1775,7 @@ static int rockchip_set_drive_perpin(struct rockchip_pin_bank *bank, bit -=16 ;break ;default : -dev_err (info->dev,"unsupported bit: %d for pinctrl drive type: %d\n" , +dev_err (dev,"unsupported bit: %d for pinctrl drive type: %d\n" , bit, drv_type);return -EINVAL ; }
@@ -1786,8 +1786,7 @@ static int rockchip_set_drive_perpin(struct rockchip_pin_bank *bank, rmask_bits =RK3288_DRV_BITS_PER_PIN ;break ;default : -dev_err (info->dev,"unsupported pinctrl drive type: %d\n" , - drv_type); +dev_err (dev,"unsupported pinctrl drive type: %d\n" , drv_type);return -EINVAL ; }
@@ -1821,6 +1820,7 @@ static int rockchip_get_pull(struct rockchip_pin_bank *bank, int pin_num) {struct rockchip_pinctrl *info = bank->drvdata;struct rockchip_pin_ctrl *ctrl = info->ctrl; +struct device *dev = info->dev;struct regmap *regmap;int reg, ret, pull_type;u8 bit;
@@ -1855,7 +1855,7 @@ static int rockchip_get_pull(struct rockchip_pin_bank *bank, int pin_num)return rockchip_pull_list[pull_type][data];default : -dev_err (info->dev,"unsupported pinctrl type\n" ); +dev_err (dev,"unsupported pinctrl type\n" );return -EINVAL ; }; }
@@ -1865,13 +1865,13 @@ static int rockchip_set_pull(struct rockchip_pin_bank *bank, {struct rockchip_pinctrl *info = bank->drvdata;struct rockchip_pin_ctrl *ctrl = info->ctrl; +struct device *dev = info->dev;struct regmap *regmap;int reg, ret, i, pull_type;u8 bit;u32 data, rmask; -dev_dbg (info->dev,"setting pull of GPIO%d-%d to %d\n" , - bank->bank_num, pin_num, pull); +dev_dbg (dev,"setting pull of GPIO%d-%d to %d\n" , bank->bank_num, pin_num, pull);/* rk3066b does support any pulls */ if (ctrl->type ==RK3066B )
@@ -1914,8 +1914,7 @@ static int rockchip_set_pull(struct rockchip_pin_bank *bank, }if (ret <0 ) { -dev_err (info->dev,"unsupported pull setting %d\n" , - pull); +dev_err (dev,"unsupported pull setting %d\n" , pull);return ret; }
@@ -1927,7 +1926,7 @@ static int rockchip_set_pull(struct rockchip_pin_bank *bank, ret =regmap_update_bits (regmap, reg, rmask, data);break ;default : -dev_err (info->dev,"unsupported pinctrl type\n" ); +dev_err (dev,"unsupported pinctrl type\n" );return -EINVAL ; }
@@ -2018,12 +2017,13 @@ static int rockchip_set_schmitt(struct rockchip_pin_bank *bank, {struct rockchip_pinctrl *info = bank->drvdata;struct rockchip_pin_ctrl *ctrl = info->ctrl; +struct device *dev = info->dev;struct regmap *regmap;int reg, ret;u8 bit;u32 data, rmask; -dev_dbg (info->dev,"setting input schmitt of GPIO%d-%d to %d\n" , +dev_dbg (dev,"setting input schmitt of GPIO%d-%d to %d\n" , bank->bank_num, pin_num, enable); ret = ctrl->schmitt_calc_reg (bank, pin_num, ®map, ®, &bit);
@@ -2083,10 +2083,11 @@ static int rockchip_pmx_set(struct pinctrl_dev *pctldev, unsigned selector,struct rockchip_pinctrl *info =pinctrl_dev_get_drvdata (pctldev);const unsigned int *pins = info->groups[group].pins;const struct rockchip_pin_config *data = info->groups[group].data; +struct device *dev = info->dev;struct rockchip_pin_bank *bank;int cnt, ret =0 ; -dev_dbg (info->dev,"enable function %s group %s\n" , +dev_dbg (dev,"enable function %s group %s\n" , info->functions[selector].name, info->groups[group].name);/*
@@ -2392,6 +2393,7 @@ static int rockchip_pinctrl_parse_groups(struct device_node *np, struct rockchip_pinctrl *info, u32 index) { +struct device *dev = info->dev;struct rockchip_pin_bank *bank;int size;const __be32 *list;
@@ -2399,7 +2401,7 @@ static int rockchip_pinctrl_parse_groups(struct device_node *np,int i, j;int ret; -dev_dbg (info->dev,"group(%d): %pOFn\n" , index, np); +dev_dbg (dev,"group(%d): %pOFn\n" , index, np);/* Initialise group */ grp->name = np->name;
@@ -2412,18 +2414,14 @@ static int rockchip_pinctrl_parse_groups(struct device_node *np,/* we do not check return since it's safe node passed down */ size /=sizeof (*list);if (!size || size %4 ) { -dev_err (info->dev,"wrong pins number or pins and configs should be by 4\n" ); +dev_err (dev,"wrong pins number or pins and configs should be by 4\n" );return -EINVAL ; } grp->npins = size /4 ; - grp->pins =devm_kcalloc (info->dev, grp->npins,sizeof (unsigned int ), -GFP_KERNEL ); - grp->data =devm_kcalloc (info->dev, - grp->npins, -sizeof (struct rockchip_pin_config ), -GFP_KERNEL ); + grp->pins =devm_kcalloc (dev, grp->npins,sizeof (*grp->pins),GFP_KERNEL ); + grp->data =devm_kcalloc (dev, grp->npins,sizeof (*grp->data),GFP_KERNEL );if (!grp->pins || !grp->data)return -ENOMEM ;
@@ -2457,6 +2455,7 @@ static int rockchip_pinctrl_parse_functions(struct device_node *np, struct rockchip_pinctrl *info, u32 index) { +struct device *dev = info->dev;struct device_node *child;struct rockchip_pmx_func *func;struct rockchip_pin_group *grp;
@@ -2464,7 +2463,7 @@ static int rockchip_pinctrl_parse_functions(struct device_node *np,static u32 grp_index;u32 i =0 ; -dev_dbg (info->dev,"parse function(%d): %pOFn\n" , index, np); +dev_dbg (dev,"parse function(%d): %pOFn\n" , index, np); func = &info->functions[index];
@@ -2474,8 +2473,7 @@ static int rockchip_pinctrl_parse_functions(struct device_node *np,if (func->ngroups <=0 )return 0 ; - func->groups =devm_kcalloc (info->dev, - func->ngroups,sizeof (char *),GFP_KERNEL ); + func->groups =devm_kcalloc (dev, func->ngroups,sizeof (*func->groups),GFP_KERNEL );if (!func->groups)return -ENOMEM ;
@@ -2503,20 +2501,14 @@ static int rockchip_pinctrl_parse_dt(struct platform_device *pdev,rockchip_pinctrl_child_count (info, np); -dev_dbg (&pdev->dev,"nfunctions = %d\n" , info->nfunctions); -dev_dbg (&pdev->dev,"ngroups = %d\n" , info->ngroups); +dev_dbg (dev,"nfunctions = %d\n" , info->nfunctions); +dev_dbg (dev,"ngroups = %d\n" , info->ngroups); - info->functions =devm_kcalloc (dev, - info->nfunctions, -sizeof (struct rockchip_pmx_func ), -GFP_KERNEL ); + info->functions =devm_kcalloc (dev, info->nfunctions,sizeof (*info->functions),GFP_KERNEL );if (!info->functions)return -ENOMEM ; - info->groups =devm_kcalloc (dev, - info->ngroups, -sizeof (struct rockchip_pin_group ), -GFP_KERNEL ); + info->groups =devm_kcalloc (dev, info->ngroups,sizeof (*info->groups),GFP_KERNEL );if (!info->groups)return -ENOMEM ;
@@ -2528,7 +2520,7 @@ static int rockchip_pinctrl_parse_dt(struct platform_device *pdev, ret =rockchip_pinctrl_parse_functions (child, info, i++);if (ret) { -dev_err (&pdev->dev,"failed to parse function\n" ); +dev_err (dev,"failed to parse function\n" );of_node_put (child);return ret; }
@@ -2543,6 +2535,7 @@ static int rockchip_pinctrl_register(struct platform_device *pdev,struct pinctrl_desc *ctrldesc = &info->pctl;struct pinctrl_pin_desc *pindesc, *pdesc;struct rockchip_pin_bank *pin_bank; +struct device *dev = &pdev->dev;int pin, bank, ret;int k;
@@ -2552,9 +2545,7 @@ static int rockchip_pinctrl_register(struct platform_device *pdev, ctrldesc->pmxops = &rockchip_pmx_ops; ctrldesc->confops = &rockchip_pinconf_ops; - pindesc =devm_kcalloc (&pdev->dev, - info->ctrl->nr_pins,sizeof (*pindesc), -GFP_KERNEL ); + pindesc =devm_kcalloc (dev, info->ctrl->nr_pins,sizeof (*pindesc),GFP_KERNEL );if (!pindesc)return -ENOMEM ;
@@ -2579,9 +2570,9 @@ static int rockchip_pinctrl_register(struct platform_device *pdev,if (ret)return ret; - info->pctl_dev =devm_pinctrl_register (&pdev->dev, ctrldesc, info); + info->pctl_dev =devm_pinctrl_register (dev, ctrldesc, info);if (IS_ERR (info->pctl_dev)) { -dev_err (&pdev->dev,"could not register pinctrl driver\n" ); +dev_err (dev,"could not register pinctrl driver\n" );return PTR_ERR (info->pctl_dev); }
@@ -2595,8 +2586,9 @@ static struct rockchip_pin_ctrl *rockchip_pinctrl_get_soc_data(struct rockchip_pinctrl *d, struct platform_device *pdev) { + struct device *dev = &pdev->dev; +struct device_node *node = dev->of_node;const struct of_device_id *match; -struct device_node *node = pdev->dev.of_node;struct rockchip_pin_ctrl *ctrl;struct rockchip_pin_bank *bank;int grf_offs, pmu_offs, drv_grf_offs, drv_pmu_offs, i, j;
@@ -2648,7 +2640,7 @@ static struct rockchip_pin_ctrl *rockchip_pinctrl_get_soc_data( drv_pmu_offs : drv_grf_offs; } -dev_dbg (d->dev,"bank %d, iomux %d has iom_offset 0x%x drv_offset 0x%x\n" , +dev_dbg (dev,"bank %d, iomux %d has iom_offset 0x%x drv_offset 0x%x\n" , i, j, iom->offset, drv->offset);/*
@@ -2757,8 +2749,8 @@ static int rockchip_pinctrl_probe(struct platform_device *pdev) {struct rockchip_pinctrl *info;struct device *dev = &pdev->dev; +struct device_node *np = dev->of_node, *node;struct rockchip_pin_ctrl *ctrl; -struct device_node *np = pdev->dev.of_node, *node;struct resource *res;void __iomem *base;int ret;
@@ -2795,8 +2787,8 @@ static int rockchip_pinctrl_probe(struct platform_device *pdev) rockchip_regmap_config.max_register =resource_size (res) -4 ; rockchip_regmap_config.name ="rockchip,pinctrl" ; - info->regmap_base =devm_regmap_init_mmio (&pdev->dev, base, - &rockchip_regmap_config); + info->regmap_base = +devm_regmap_init_mmio (dev, base, &rockchip_regmap_config);/* to check for the old dt-bindings */ info->reg_size =resource_size (res);
@@ -2808,12 +2800,10 @@ static int rockchip_pinctrl_probe(struct platform_device *pdev)if (IS_ERR (base))return PTR_ERR (base); - rockchip_regmap_config.max_register = -resource_size (res) -4 ; + rockchip_regmap_config.max_register =resource_size (res) -4 ; rockchip_regmap_config.name ="rockchip,pinctrl-pull" ; - info->regmap_pull =devm_regmap_init_mmio (&pdev->dev, - base, - &rockchip_regmap_config); + info->regmap_pull = +devm_regmap_init_mmio (dev, base, &rockchip_regmap_config); } }
@@ -2834,7 +2824,7 @@ static int rockchip_pinctrl_probe(struct platform_device *pdev) ret =of_platform_populate (np,NULL ,NULL , &pdev->dev);if (ret) { -dev_err (&pdev->dev,"failed to register gpio device\n" ); +dev_err (dev,"failed to register gpio device\n" );return ret; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 47/204 pinctrl/rockchip: add error handling for pull/drive register getters
In reply to Greg Kroah-HartmanFrom: Sebastian Reichel <[email protected]>
[ Upstream commit 42573ab3b9f94fbeba8b84e142703ea551624f6d ]
Add error handling for the pull and driver register getters in preparation for RK3588 support.
Stable-dep-of: 31b62a98de42 ("pinctrl: rockchip: fix reading pull type on rk3568")
--- drivers/pinctrl/pinctrl-rockchip.c | 168 ++++++++++++++++++----------- drivers/pinctrl/pinctrl-rockchip.h | 4 +- 2 files changed, 109 insertions(+), 63 deletions(-)
drivers/pinctrl/pinctrl-rockchip.c +107 -61
@@ -1039,9 +1039,9 @@ static int rockchip_set_mux(struct rockchip_pin_bank *bank, int pin, int mux)#define PX30_PULL_PINS_PER_REG 8#define PX30_PULL_BANK_STRIDE 16 -static void px30_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int px30_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1061,6 +1061,8 @@ static void px30_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *reg += ((pin_num /PX30_PULL_PINS_PER_REG ) *4 ); *bit = (pin_num %PX30_PULL_PINS_PER_REG ); *bit *=PX30_PULL_BITS_PER_PIN ; + +return 0 ; }#define PX30_DRV_PMU_OFFSET 0x20
@@ -1069,9 +1071,9 @@ static void px30_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank,#define PX30_DRV_PINS_PER_REG 8#define PX30_DRV_BANK_STRIDE 16 -static void px30_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int px30_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1091,6 +1093,8 @@ static void px30_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *reg += ((pin_num /PX30_DRV_PINS_PER_REG ) *4 ); *bit = (pin_num %PX30_DRV_PINS_PER_REG ); *bit *=PX30_DRV_BITS_PER_PIN ; + +return 0 ; }#define PX30_SCHMITT_PMU_OFFSET 0x38
@@ -1130,9 +1134,9 @@ static int px30_calc_schmitt_reg_and_bit(struct rockchip_pin_bank *bank,#define RV1108_PULL_BITS_PER_PIN 2#define RV1108_PULL_BANK_STRIDE 16 -static void rv1108_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rv1108_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1151,6 +1155,8 @@ static void rv1108_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *reg += ((pin_num /RV1108_PULL_PINS_PER_REG ) *4 ); *bit = (pin_num %RV1108_PULL_PINS_PER_REG ); *bit *=RV1108_PULL_BITS_PER_PIN ; + +return 0 ; }#define RV1108_DRV_PMU_OFFSET 0x20
@@ -1159,9 +1165,9 @@ static void rv1108_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank,#define RV1108_DRV_PINS_PER_REG 8#define RV1108_DRV_BANK_STRIDE 16 -static void rv1108_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rv1108_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1181,6 +1187,8 @@ static void rv1108_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *reg += ((pin_num /RV1108_DRV_PINS_PER_REG ) *4 ); *bit = pin_num %RV1108_DRV_PINS_PER_REG ; *bit *=RV1108_DRV_BITS_PER_PIN ; + +return 0 ; }#define RV1108_SCHMITT_PMU_OFFSET 0x30
@@ -1237,9 +1245,9 @@ static int rk3308_calc_schmitt_reg_and_bit(struct rockchip_pin_bank *bank,#define RK2928_PULL_PINS_PER_REG 16#define RK2928_PULL_BANK_STRIDE 8 -static void rk2928_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk2928_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1249,13 +1257,15 @@ static void rk2928_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *reg += (pin_num /RK2928_PULL_PINS_PER_REG ) *4 ; *bit = pin_num %RK2928_PULL_PINS_PER_REG ; + +return 0 ; };#define RK3128_PULL_OFFSET 0x118 -static void rk3128_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3128_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1265,6 +1275,8 @@ static void rk3128_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *reg += ((pin_num /RK2928_PULL_PINS_PER_REG ) *4 ); *bit = pin_num %RK2928_PULL_PINS_PER_REG ; + +return 0 ; }#define RK3188_PULL_OFFSET 0x164
@@ -1273,9 +1285,9 @@ static void rk3128_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank,#define RK3188_PULL_BANK_STRIDE 16#define RK3188_PULL_PMU_OFFSET 0x64 -static void rk3188_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3188_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1305,12 +1317,14 @@ static void rk3188_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit =7 - (pin_num %RK3188_PULL_PINS_PER_REG ); *bit *=RK3188_PULL_BITS_PER_PIN ; } + +return 0 ; }#define RK3288_PULL_OFFSET 0x140 -static void rk3288_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3288_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1334,6 +1348,8 @@ static void rk3288_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3188_PULL_PINS_PER_REG ); *bit *=RK3188_PULL_BITS_PER_PIN ; } + +return 0 ; }#define RK3288_DRV_PMU_OFFSET 0x70
@@ -1342,9 +1358,9 @@ static void rk3288_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank,#define RK3288_DRV_PINS_PER_REG 8#define RK3288_DRV_BANK_STRIDE 16 -static void rk3288_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3288_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1368,13 +1384,15 @@ static void rk3288_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3288_DRV_PINS_PER_REG ); *bit *=RK3288_DRV_BITS_PER_PIN ; } + +return 0 ; }#define RK3228_PULL_OFFSET 0x100 -static void rk3228_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3228_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1385,13 +1403,15 @@ static void rk3228_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3188_PULL_PINS_PER_REG ); *bit *=RK3188_PULL_BITS_PER_PIN ; + +return 0 ; }#define RK3228_DRV_GRF_OFFSET 0x200 -static void rk3228_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3228_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1402,13 +1422,15 @@ static void rk3228_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3288_DRV_PINS_PER_REG ); *bit *=RK3288_DRV_BITS_PER_PIN ; + +return 0 ; }#define RK3308_PULL_OFFSET 0xa0 -static void rk3308_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3308_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1419,13 +1441,15 @@ static void rk3308_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3188_PULL_PINS_PER_REG ); *bit *=RK3188_PULL_BITS_PER_PIN ; + +return 0 ; }#define RK3308_DRV_GRF_OFFSET 0x100 -static void rk3308_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3308_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1436,14 +1460,16 @@ static void rk3308_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3288_DRV_PINS_PER_REG ); *bit *=RK3288_DRV_BITS_PER_PIN ; + +return 0 ; }#define RK3368_PULL_GRF_OFFSET 0x100#define RK3368_PULL_PMU_OFFSET 0x10 -static void rk3368_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3368_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1467,14 +1493,16 @@ static void rk3368_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3188_PULL_PINS_PER_REG ); *bit *=RK3188_PULL_BITS_PER_PIN ; } + +return 0 ; }#define RK3368_DRV_PMU_OFFSET 0x20#define RK3368_DRV_GRF_OFFSET 0x200 -static void rk3368_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3368_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1498,15 +1526,17 @@ static void rk3368_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3288_DRV_PINS_PER_REG ); *bit *=RK3288_DRV_BITS_PER_PIN ; } + +return 0 ; }#define RK3399_PULL_GRF_OFFSET 0xe040#define RK3399_PULL_PMU_OFFSET 0x40#define RK3399_DRV_3BITS_PER_PIN 3 -static void rk3399_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3399_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1532,11 +1562,13 @@ static void rk3399_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3188_PULL_PINS_PER_REG ); *bit *=RK3188_PULL_BITS_PER_PIN ; } + +return 0 ; } -static void rk3399_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3399_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;int drv_num = (pin_num /8 );
@@ -1553,6 +1585,8 @@ static void rk3399_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %8 ) *3 ; else *bit = (pin_num %8 ) *2 ; + +return 0 ; }#define RK3568_PULL_PMU_OFFSET 0x20
@@ -1561,9 +1595,9 @@ static void rk3399_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank,#define RK3568_PULL_PINS_PER_REG 8#define RK3568_PULL_BANK_STRIDE 0x10 -static void rk3568_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3568_calc_pull_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1584,6 +1618,8 @@ static void rk3568_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3568_PULL_PINS_PER_REG ); *bit *=RK3568_PULL_BITS_PER_PIN ; } + +return 0 ; }#define RK3568_DRV_PMU_OFFSET 0x70
@@ -1592,9 +1628,9 @@ static void rk3568_calc_pull_reg_and_bit(struct rockchip_pin_bank *bank,#define RK3568_DRV_PINS_PER_REG 2#define RK3568_DRV_BANK_STRIDE 0x40 -static void rk3568_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, -int pin_num,struct regmap **regmap, -int *reg,u8 *bit) +static int rk3568_calc_drv_reg_and_bit (struct rockchip_pin_bank *bank, +int pin_num,struct regmap **regmap, +int *reg,u8 *bit) {struct rockchip_pinctrl *info = bank->drvdata;
@@ -1615,6 +1651,8 @@ static void rk3568_calc_drv_reg_and_bit(struct rockchip_pin_bank *bank, *bit = (pin_num %RK3568_DRV_PINS_PER_REG ); *bit *=RK3568_DRV_BITS_PER_PIN ; } + +return 0 ; }static int rockchip_perpin_drv_list[DRV_TYPE_MAX ][8 ] = {
@@ -1637,7 +1675,9 @@ static int rockchip_get_drive_perpin(struct rockchip_pin_bank *bank,u8 bit;int drv_type = bank->drv[pin_num /8 ].drv_type; - ctrl->drv_calc_reg (bank, pin_num, ®map, ®, &bit); + ret = ctrl->drv_calc_reg (bank, pin_num, ®map, ®, &bit); +if (ret) +return ret;switch (drv_type) {case DRV_TYPE_IO_1V8_3V0_AUTO :
@@ -1717,7 +1757,9 @@ static int rockchip_set_drive_perpin(struct rockchip_pin_bank *bank,dev_dbg (dev,"setting drive of GPIO%d-%d to %d\n" , bank->bank_num, pin_num, strength); - ctrl->drv_calc_reg (bank, pin_num, ®map, ®, &bit); + ret = ctrl->drv_calc_reg (bank, pin_num, ®map, ®, &bit); +if (ret) +return ret;if (ctrl->type ==RK3568 ) { rmask_bits =RK3568_DRV_BITS_PER_PIN ; ret = (1 << (strength +1 )) -1 ;
@@ -1830,7 +1872,9 @@ static int rockchip_get_pull(struct rockchip_pin_bank *bank, int pin_num)if (ctrl->type ==RK3066B )return PIN_CONFIG_BIAS_DISABLE ; - ctrl->pull_calc_reg (bank, pin_num, ®map, ®, &bit); + ret = ctrl->pull_calc_reg (bank, pin_num, ®map, ®, &bit); +if (ret) +return ret; ret =regmap_read (regmap, reg, &data);if (ret)
@@ -1877,7 +1921,9 @@ static int rockchip_set_pull(struct rockchip_pin_bank *bank,if (ctrl->type ==RK3066B )return pull ? -EINVAL :0 ; - ctrl->pull_calc_reg (bank, pin_num, ®map, ®, &bit); + ret = ctrl->pull_calc_reg (bank, pin_num, ®map, ®, &bit); +if (ret) +return ret;switch (ctrl->type) {case RK2928 :
drivers/pinctrl/pinctrl-rockchip.h +2 -2
@@ -230,10 +230,10 @@ struct rockchip_pin_ctrl {struct rockchip_mux_route_data *iomux_routes;u32 niomux_routes; -void (*pull_calc_reg)(struct rockchip_pin_bank *bank, +int (*pull_calc_reg)(struct rockchip_pin_bank *bank,int pin_num,struct regmap **regmap,int *reg,u8 *bit); -void (*drv_calc_reg)(struct rockchip_pin_bank *bank, +int (*drv_calc_reg)(struct rockchip_pin_bank *bank,int pin_num,struct regmap **regmap,int *reg,u8 *bit); int (*schmitt_calc_reg)(struct rockchip_pin_bank *bank,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 48/204 pinctrl: rockchip: fix reading pull type on rk3568
In reply to Greg Kroah-HartmanFrom: Jonas Karlman <[email protected]>
[ Upstream commit 31b62a98de42cf65d76e4dcfb571af067d27d83a ]
When reading pinconf-pins from debugfs it fails to get the configured pull type on RK3568, "unsupported pinctrl type" error messages is also reported.
Fix this by adding support for RK3568 in rockchip_get_pull, including a reverse of the pull-up value swap applied in rockchip_set_pull so that pull-up is correctly reported in pinconf-pins.
Also update the workaround comment to reflect affected pins, GPIO0_D3-D6.
--- drivers/pinctrl/pinctrl-rockchip.c | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-)
drivers/pinctrl/pinctrl-rockchip.c +10 -1
@@ -1893,9 +1893,18 @@ static int rockchip_get_pull(struct rockchip_pin_bank *bank, int pin_num)case RK3308 :case RK3368 :case RK3399 : +case RK3568 : pull_type = bank->pull_type[pin_num /8 ]; data >>= bit; data &= (1 <<RK3188_PULL_BITS_PER_PIN ) -1 ; +/* +* In the TRM, pull-up being 1 for everything except the GPIO0_D3-D6, +* where that pull up value becomes 3. +*/ +if (ctrl->type ==RK3568 && bank->bank_num ==0 && pin_num >=27 && pin_num <=30 ) { +if (data ==3 ) + data =1 ; + }return rockchip_pull_list[pull_type][data];default :
@@ -1951,7 +1960,7 @@ static int rockchip_set_pull(struct rockchip_pin_bank *bank, } }/* -* In the TRM, pull-up being 1 for everything except the GPIO0_D0-D6, +* In the TRM, pull-up being 1 for everything except the GPIO0_D3-D6, * where that pull up value becomes 3. */ if (ctrl->type ==RK3568 && bank->bank_num ==0 && pin_num >=27 && pin_num <=30 ) {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 49/204 net: stmmac: Fix queue statistics reading
In reply to Greg Kroah-HartmanFrom: Kurt Kanzenbach <[email protected]>
[ Upstream commit c296c77efb66994d94d9f706446a115581226550 ]
Correct queue statistics reading. All queue statistics are stored as unsigned long values. The retrieval for ethtool fetches these values as u64. However, on some systems the size of the counters are 32 bit. That yields wrong queue statistic counters e.g., on arm32 systems such as the stm32mp157. Fix it by using the correct data type.
Tested on Olimex STMP157-OLinuXino-LIME2 by simple running linuxptp for a short period of time:
Non-patched kernel:
|root@st1:~# ethtool -S eth0 | grep q0 | q0_tx_pkt_n: 3775276254951 # ??? | q0_tx_irq_n: 879 | q0_rx_pkt_n: 1194000908909 # ??? | q0_rx_irq_n: 278
Patched kernel:
|root@st1:~# ethtool -S eth0 | grep q0 | q0_tx_pkt_n: 2434 | q0_tx_irq_n: 1274 | q0_rx_pkt_n: 1604 | q0_rx_irq_n: 846
--- drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
drivers/net/ethernet/stmicro/stmmac/stmmac_ethtool.c +4 -4
@@ -548,16 +548,16 @@ static void stmmac_get_per_qstats(struct stmmac_priv *priv, u64 *data) p = (char *)priv + offsetof(struct stmmac_priv , xstats.txq_stats[q].tx_pkt_n);for (stat =0 ; stat <STMMAC_TXQ_STATS ; stat++) { - *data++ = (*(u64 *)p); - p +=sizeof (u64 *); + *data++ = (*(unsigned long *)p); + p +=sizeof (unsigned long ); } }for (q =0 ; q < rx_cnt; q++) { p = (char *)priv + offsetof(struct stmmac_priv , xstats.rxq_stats[q].rx_pkt_n);for (stat =0 ; stat <STMMAC_RXQ_STATS ; stat++) { - *data++ = (*(u64 *)p); - p +=sizeof (u64 *); + *data++ = (*(unsigned long *)p); + p +=sizeof (unsigned long ); } } }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 50/204 net/sched: sch_taprio: fix possible use-after-free
In reply to Greg Kroah-HartmanFrom: Eric Dumazet <[email protected]>
[ Upstream commit 3a415d59c1dbec9d772dbfab2d2520d98360caae ]
syzbot reported a nasty crash [1] in net_tx_action() which made little sense until we got a repro.
This repro installs a taprio qdisc, but providing an invalid TCA_RATE attribute.
qdisc_create() has to destroy the just initialized taprio qdisc, and taprio_destroy() is called.
However, the hrtimer used by taprio had already fired, therefore advance_sched() called __netif_schedule().
Then net_tx_action was trying to use a destroyed qdisc.
We can not undo the __netif_schedule(), so we must wait until one cpu serviced the qdisc before we can proceed.
Many thanks to Alexander Potapenko for his help.
[1]
BUG: KMSAN: uninit-value in queued_spin_trylock include/asm-generic/qspinlock.h:94 [inline] BUG: KMSAN: uninit-value in do_raw_spin_trylock include/linux/spinlock.h:191 [inline] BUG: KMSAN: uninit-value in __raw_spin_trylock include/linux/spinlock_api_smp.h:89 [inline] BUG: KMSAN: uninit-value in _raw_spin_trylock+0x92/0xa0 kernel/locking/spinlock.c:138 queued_spin_trylock include/asm-generic/qspinlock.h:94 [inline] do_raw_spin_trylock include/linux/spinlock.h:191 [inline] __raw_spin_trylock include/linux/spinlock_api_smp.h:89 [inline] _raw_spin_trylock+0x92/0xa0 kernel/locking/spinlock.c:138 spin_trylock include/linux/spinlock.h:359 [inline] qdisc_run_begin include/net/sch_generic.h:187 [inline] qdisc_run+0xee/0x540 include/net/pkt_sched.h:125 net_tx_action+0x77c/0x9a0 net/core/dev.c:5086 __do_softirq+0x1cc/0x7fb kernel/softirq.c:571 run_ksoftirqd+0x2c/0x50 kernel/softirq.c:934 smpboot_thread_fn+0x554/0x9f0 kernel/smpboot.c:164 kthread+0x31b/0x430 kernel/kthread.c:376 ret_from_fork+0x1f/0x30
Uninit was created at:
slab_post_alloc_hook mm/slab.h:732 [inline] slab_alloc_node mm/slub.c:3258 [inline] __kmalloc_node_track_caller+0x814/0x1250 mm/slub.c:4970 kmalloc_reserve net/core/skbuff.c:358 [inline] __alloc_skb+0x346/0xcf0 net/core/skbuff.c:430 alloc_skb include/linux/skbuff.h:1257 [inline] nlmsg_new include/net/netlink.h:953 [inline] netlink_ack+0x5f3/0x12b0 net/netlink/af_netlink.c:2436 netlink_rcv_skb+0x55d/0x6c0 net/netlink/af_netlink.c:2507 rtnetlink_rcv+0x30/0x40 net/core/rtnetlink.c:6108 netlink_unicast_kernel net/netlink/af_netlink.c:1319 [inline] netlink_unicast+0xf3b/0x1270 net/netlink/af_netlink.c:1345 netlink_sendmsg+0x1288/0x1440 net/netlink/af_netlink.c:1921 sock_sendmsg_nosec net/socket.c:714 [inline] sock_sendmsg net/socket.c:734 [inline] ____sys_sendmsg+0xabc/0xe90 net/socket.c:2482 ___sys_sendmsg+0x2a1/0x3f0 net/socket.c:2536 __sys_sendmsg net/socket.c:2565 [inline] __do_sys_sendmsg net/socket.c:2574 [inline] __se_sys_sendmsg net/socket.c:2572 [inline] __x64_sys_sendmsg+0x367/0x540 net/socket.c:2572 do_syscall_x64 arch/x86/entry/common.c:50 [inline] do_syscall_64+0x3d/0xb0 arch/x86/entry/common.c:80 entry_SYSCALL_64_after_hwframe+0x63/0xcd CPU: 0 PID: 13 Comm: ksoftirqd/0 Not tainted 6.0.0-rc2-syzkaller-47461-gac3859c02d7f #0 Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 07/22/2022
--- include/net/sch_generic.h | 7 +++++++ net/sched/sch_taprio.c | 3 +++ 2 files changed, 10 insertions(+)
include/net/sch_generic.h +7 -0
@@ -1335,4 +1335,11 @@ void mini_qdisc_pair_block_init(struct mini_Qdisc_pair *miniqp,int sch_frag_xmit_hook (struct sk_buff *skb,int (*xmit)(struct sk_buff *skb)); +/* Make sure qdisc is no longer in SCHED state. */ +static inline void qdisc_synchronize (const struct Qdisc *q) +{ +while (test_bit (__QDISC_STATE_SCHED, &q->state)) +msleep (1 ); +} +#endif
net/sched/sch_taprio.c +3 -0
@@ -1632,6 +1632,8 @@ static void taprio_reset(struct Qdisc *sch)int i;hrtimer_cancel (&q->advance_timer); +qdisc_synchronize (sch); +if (q->qdiscs) {for (i =0 ; i < dev->num_tx_queues; i++)if (q->qdiscs[i])
@@ -1653,6 +1655,7 @@ static void taprio_destroy(struct Qdisc *sch)* happens in qdisc_create(), after taprio_init() has been called. */ hrtimer_cancel (&q->advance_timer); +qdisc_synchronize (sch);taprio_disable_offload (dev, q,NULL );
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 51/204 l2tp: Serialize access to sk_user_data with sk_callback_lock
In reply to Greg Kroah-HartmanFrom: Jakub Sitnicki <[email protected]>
[ Upstream commit b68777d54fac21fc833ec26ea1a2a84f975ab035 ]
sk->sk_user_data has multiple users, which are not compatible with each other. Writers must synchronize by grabbing the sk->sk_callback_lock.
l2tp currently fails to grab the lock when modifying the underlying tunnel socket fields. Fix it by adding appropriate locking.
We err on the side of safety and grab the sk_callback_lock also inside the sk_destruct callback overridden by l2tp, even though there should be no refs allowing access to the sock at the time when sk_destruct gets called.
v4:
- serialize write to sk_user_data in l2tp sk_destruct
v3:
- switch from sock lock to sk_callback_lock
- document write-protection for sk_user_data
v2:
- update Fixes to point to origin of the bug
- use real names in Reported/Tested-by tags
Stable-dep-of: 0b2c59720e65 ("l2tp: close all race conditions in l2tp_tunnel_register()")
--- include/net/sock.h | 2 +- net/l2tp/l2tp_core.c | 19 +++++++++++++------ 2 files changed, 14 insertions(+), 7 deletions(-)
include/net/sock.h +1 -1
@@ -323,7 +323,7 @@ struct bpf_local_storage;* @sk_tskey: counter to disambiguate concurrent tstamp requests * @sk_zckey: counter to order MSG_ZEROCOPY notifications * @sk_socket: Identd and reporting IO signals -* @sk_user_data: RPC layer private data +* @sk_user_data: RPC layer private data. Write-protected by @sk_callback_lock. * @sk_frag: cached page frag * @sk_peek_off: current peek_offset value * @sk_send_head: front of stuff to transmit
net/l2tp/l2tp_core.c +13 -6
@@ -1150,8 +1150,10 @@ static void l2tp_tunnel_destruct(struct sock *sk) }/* Remove hooks into tunnel socket */ +write_lock_bh (&sk->sk_callback_lock); sk->sk_destruct = tunnel->old_sk_destruct; sk->sk_user_data =NULL ; +write_unlock_bh (&sk->sk_callback_lock);/* Call the original destructor */ if (sk->sk_destruct)
@@ -1471,16 +1473,18 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net, sock =sockfd_lookup (tunnel->fd, &ret);if (!sock) goto err; - - ret =l2tp_validate_socket (sock->sk, net, tunnel->encap); -if (ret <0 ) - goto err_sock; } + sk = sock->sk; +write_lock (&sk->sk_callback_lock); + + ret =l2tp_validate_socket (sk, net, tunnel->encap); +if (ret <0 ) + goto err_sock; + tunnel->l2tp_net = net; pn =l2tp_pernet (net); - sk = sock->sk;sock_hold (sk); tunnel->sock = sk;
@@ -1506,7 +1510,7 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,setup_udp_tunnel_sock (net, sock, &udp_cfg); }else { - sk->sk_user_data = tunnel; +rcu_assign_sk_user_data (sk, tunnel); } tunnel->old_sk_destruct = sk->sk_destruct;
@@ -1520,6 +1524,7 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,if (tunnel->fd >=0 )sockfd_put (sock); +write_unlock (&sk->sk_callback_lock);return 0 ; err_sock:
@@ -1527,6 +1532,8 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,sock_release (sock); elsesockfd_put (sock ); + +write_unlock (&sk->sk_callback_lock); err:return ret; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 52/204 l2tp: Dont sleep and disable BH under writer-side sk_callback_lock
In reply to Greg Kroah-HartmanFrom: Jakub Sitnicki <[email protected]>
[ Upstream commit af295e854a4e3813ffbdef26dbb6a4d6226c3ea1 ]
When holding a reader-writer spin lock we cannot sleep. Calling setup_udp_tunnel_sock() with write lock held violates this rule, because we end up calling percpu_down_read(), which might sleep, as syzbot reports [1]:
__might_resched.cold+0x222/0x26b kernel/sched/core.c:9890 percpu_down_read include/linux/percpu-rwsem.h:49 [inline] cpus_read_lock+0x1b/0x140 kernel/cpu.c:310 static_key_slow_inc+0x12/0x20 kernel/jump_label.c:158 udp_tunnel_encap_enable include/net/udp_tunnel.h:187 [inline] setup_udp_tunnel_sock+0x43d/0x550 net/ipv4/udp_tunnel_core.c:81 l2tp_tunnel_register+0xc51/0x1210 net/l2tp/l2tp_core.c:1509 pppol2tp_connect+0xcdc/0x1a10 net/l2tp/l2tp_ppp.c:723
Trim the writer-side critical section for sk_callback_lock down to the minimum, so that it covers only operations on sk_user_data.
Also, when grabbing the sk_callback_lock, we always need to disable BH, as Eric points out. Failing to do so leads to deadlocks because we acquire sk_callback_lock in softirq context, which can get stuck waiting on us if:
1) it runs on the same CPU, or
CPU0
----
lock(clock-AF_INET6);
<Interrupt>
lock(clock-AF_INET6);2) lock ordering leads to priority inversion
CPU0 CPU1
---- ----
lock(clock-AF_INET6);
local_irq_disable();
lock(&tcp_hashinfo.bhash[i].lock);
lock(clock-AF_INET6);
<Interrupt>
lock(&tcp_hashinfo.bhash[i].lock);... as syzbot reports [2,3]. Use the _bh variants for write_(un)lock.
[1] https://lore.kernel.org/netdev/[email protected]/
[2] https://lore.kernel.org/netdev/[email protected]/
[3] https://lore.kernel.org/netdev/[email protected]/
v2:
- Check and set sk_user_data while holding sk_callback_lock for both L2TP encapsulation types (IP and UDP) (Tetsuo)
Stable-dep-of: 0b2c59720e65 ("l2tp: close all race conditions in l2tp_tunnel_register()")
--- net/l2tp/l2tp_core.c | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-)
net/l2tp/l2tp_core.c +9 -8
@@ -1476,11 +1476,12 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net, } sk = sock->sk; -write_lock (&sk->sk_callback_lock); - +write_lock_bh (&sk->sk_callback_lock); ret =l2tp_validate_socket (sk, net, tunnel->encap);if (ret <0 ) - goto err_sock; + goto err_inval_sock; +rcu_assign_sk_user_data (sk, tunnel); +write_unlock_bh (&sk->sk_callback_lock); tunnel->l2tp_net = net; pn =l2tp_pernet (net);
@@ -1509,8 +1510,6 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net, };setup_udp_tunnel_sock (net, sock, &udp_cfg); - }else { -rcu_assign_sk_user_data (sk, tunnel); } tunnel->old_sk_destruct = sk->sk_destruct;
@@ -1524,16 +1523,18 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,if (tunnel->fd >=0 )sockfd_put (sock); -write_unlock (&sk->sk_callback_lock);return 0 ; err_sock: +write_lock_bh (&sk->sk_callback_lock); +rcu_assign_sk_user_data (sk,NULL ); +err_inval_sock: +write_unlock_bh (&sk->sk_callback_lock); +if (tunnel->fd <0 )sock_release (sock);else sockfd_put (sock); - -write_unlock (&sk->sk_callback_lock); err:return ret; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 53/204 l2tp: convert l2tp_tunnel_list to idr
In reply to Greg Kroah-HartmanFrom: Cong Wang <[email protected]>
[ Upstream commit c4d48a58f32c5972174a1d01c33b296fe378cce0 ]
l2tp uses l2tp_tunnel_list to track all registered tunnels and to allocate tunnel ID's. IDR can do the same job.
More importantly, with IDR we can hold the ID before a successful registration so that we don't need to worry about late error handling, it is not easy to rollback socket changes.
This is a preparation for the following fix.
Stable-dep-of: 0b2c59720e65 ("l2tp: close all race conditions in l2tp_tunnel_register()")
--- net/l2tp/l2tp_core.c | 85 ++++++++++++++++++++++---------------------- 1 file changed, 42 insertions(+), 43 deletions(-)
net/l2tp/l2tp_core.c +42 -43
@@ -104,9 +104,9 @@ static struct workqueue_struct *l2tp_wq;/* per-net private data for this module */ static unsigned int l2tp_net_id;struct l2tp_net { -struct list_head l2tp_tunnel_list; -/* Lock for write access to l2tp_tunnel_list */ -spinlock_t l2tp_tunnel_list_lock; +/* Lock for write access to l2tp_tunnel_idr */ +spinlock_t l2tp_tunnel_idr_lock; +struct idr l2tp_tunnel_idr;struct hlist_head l2tp_session_hlist[L2TP_HASH_SIZE_2 ];/* Lock for write access to l2tp_session_hlist */ spinlock_t l2tp_session_hlist_lock;
@@ -208,13 +208,10 @@ struct l2tp_tunnel *l2tp_tunnel_get(const struct net *net, u32 tunnel_id)struct l2tp_tunnel *tunnel;rcu_read_lock_bh (); -list_for_each_entry_rcu (tunnel, &pn->l2tp_tunnel_list, list) { -if (tunnel->tunnel_id == tunnel_id && -refcount_inc_not_zero (&tunnel->ref_count)) { -rcu_read_unlock_bh (); - -return tunnel; - } + tunnel =idr_find (&pn->l2tp_tunnel_idr, tunnel_id); +if (tunnel &&refcount_inc_not_zero (&tunnel->ref_count)) { +rcu_read_unlock_bh (); +return tunnel; }rcu_read_unlock_bh ();
@@ -224,13 +221,14 @@ EXPORT_SYMBOL_GPL(l2tp_tunnel_get);struct l2tp_tunnel *l2tp_tunnel_get_nth (const struct net *net,int nth) { -const struct l2tp_net *pn =l2tp_pernet (net); +struct l2tp_net *pn =l2tp_pernet (net); +unsigned long tunnel_id, tmp;struct l2tp_tunnel *tunnel;int count =0 ;rcu_read_lock_bh (); -list_for_each_entry_rcu (tunnel, &pn->l2tp_tunnel_list, list) { -if (++count > nth && +idr_for_each_entry_ul (&pn->l2tp_tunnel_idr, tunnel, tmp, tunnel_id) { +if (tunnel && ++count > nth &&refcount_inc_not_zero (&tunnel->ref_count)) {rcu_read_unlock_bh ();return tunnel;
@@ -1229,6 +1227,15 @@ static void l2tp_udp_encap_destroy(struct sock *sk)l2tp_tunnel_delete (tunnel); } +static void l2tp_tunnel_remove (struct net *net,struct l2tp_tunnel *tunnel) +{ +struct l2tp_net *pn =l2tp_pernet (net); + +spin_lock_bh (&pn->l2tp_tunnel_idr_lock); +idr_remove (&pn->l2tp_tunnel_idr, tunnel->tunnel_id); +spin_unlock_bh (&pn->l2tp_tunnel_idr_lock); +} +/* Workqueue tunnel deletion function */ static void l2tp_tunnel_del_work (struct work_struct *work) {
@@ -1236,7 +1243,6 @@ static void l2tp_tunnel_del_work(struct work_struct *work) del_work);struct sock *sk = tunnel->sock;struct socket *sock = sk->sk_socket; -struct l2tp_net *pn;l2tp_tunnel_closeall (tunnel);
@@ -1250,12 +1256,7 @@ static void l2tp_tunnel_del_work(struct work_struct *work) } } -/* Remove the tunnel struct from the tunnel list */ - pn =l2tp_pernet (tunnel->l2tp_net); -spin_lock_bh (&pn->l2tp_tunnel_list_lock); -list_del_rcu (&tunnel->list); -spin_unlock_bh (&pn->l2tp_tunnel_list_lock); - +l2tp_tunnel_remove (tunnel->l2tp_net, tunnel);/* drop initial ref */ l2tp_tunnel_dec_refcount (tunnel);
@@ -1457,12 +1458,19 @@ static int l2tp_validate_socket(const struct sock *sk, const struct net *net,int l2tp_tunnel_register (struct l2tp_tunnel *tunnel,struct net *net,struct l2tp_tunnel_cfg *cfg) { -struct l2tp_tunnel *tunnel_walk; -struct l2tp_net *pn; +struct l2tp_net *pn =l2tp_pernet (net); +u32 tunnel_id = tunnel->tunnel_id;struct socket *sock;struct sock *sk;int ret; +spin_lock_bh (&pn->l2tp_tunnel_idr_lock); + ret =idr_alloc_u32 (&pn->l2tp_tunnel_idr,NULL , &tunnel_id, tunnel_id, +GFP_ATOMIC ); +spin_unlock_bh (&pn->l2tp_tunnel_idr_lock); +if (ret) +return ret == -ENOSPC ? -EEXIST : ret; +if (tunnel->fd <0 ) { ret = l2tp_tunnel_sock_create(net, tunnel->tunnel_id, tunnel->peer_tunnel_id, cfg,
@@ -1483,23 +1491,13 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,rcu_assign_sk_user_data (sk, tunnel);write_unlock_bh (&sk->sk_callback_lock); - tunnel->l2tp_net = net; - pn =l2tp_pernet (net); -sock_hold (sk); tunnel->sock = sk; + tunnel->l2tp_net = net; -spin_lock_bh (&pn->l2tp_tunnel_list_lock); -list_for_each_entry (tunnel_walk, &pn->l2tp_tunnel_list, list) { -if (tunnel_walk->tunnel_id == tunnel->tunnel_id) { -spin_unlock_bh (&pn->l2tp_tunnel_list_lock); -sock_put (sk); - ret = -EEXIST ; - goto err_sock; - } - } -list_add_rcu (&tunnel->list, &pn->l2tp_tunnel_list); -spin_unlock_bh (&pn->l2tp_tunnel_list_lock); +spin_lock_bh (&pn->l2tp_tunnel_idr_lock); +idr_replace (&pn->l2tp_tunnel_idr, tunnel, tunnel->tunnel_id); +spin_unlock_bh (&pn->l2tp_tunnel_idr_lock);if (tunnel->encap ==L2TP_ENCAPTYPE_UDP ) {struct udp_tunnel_sock_cfg udp_cfg = {
@@ -1525,9 +1523,6 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,return 0 ; -err_sock: -write_lock_bh (&sk->sk_callback_lock); -rcu_assign_sk_user_data (sk,NULL ); err_inval_sock:write_unlock_bh (&sk->sk_callback_lock);
@@ -1536,6 +1531,7 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,else sockfd_put (sock); err: +l2tp_tunnel_remove (net, tunnel);return ret; }EXPORT_SYMBOL_GPL (l2tp_tunnel_register);
@@ -1649,8 +1645,8 @@ static __net_init int l2tp_init_net(struct net *net)struct l2tp_net *pn =net_generic (net, l2tp_net_id);int hash; -INIT_LIST_HEAD (&pn->l2tp_tunnel_list); -spin_lock_init (&pn->l2tp_tunnel_list_lock); +idr_init (&pn->l2tp_tunnel_idr); +spin_lock_init (&pn->l2tp_tunnel_idr_lock);for (hash =0 ; hash <L2TP_HASH_SIZE_2 ; hash++)INIT_HLIST_HEAD (&pn->l2tp_session_hlist[hash]);
@@ -1664,11 +1660,13 @@ static __net_exit void l2tp_exit_net(struct net *net) {struct l2tp_net *pn =l2tp_pernet (net);struct l2tp_tunnel *tunnel =NULL ; +unsigned long tunnel_id, tmp;int hash;rcu_read_lock_bh (); -list_for_each_entry_rcu (tunnel, &pn->l2tp_tunnel_list, list) { -l2tp_tunnel_delete (tunnel); +idr_for_each_entry_ul (&pn->l2tp_tunnel_idr, tunnel, tmp, tunnel_id) { +if (tunnel) +l2tp_tunnel_delete (tunnel); }rcu_read_unlock_bh ();
@@ -1678,6 +1676,7 @@ static __net_exit void l2tp_exit_net(struct net *net)for (hash =0 ; hash <L2TP_HASH_SIZE_2 ; hash++)WARN_ON_ONCE (!hlist_empty (&pn->l2tp_session_hlist[hash])); +idr_destroy (&pn->l2tp_tunnel_idr); }static struct pernet_operations l2tp_net_ops = {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 54/204 l2tp: close all race conditions in l2tp_tunnel_register()
In reply to Greg Kroah-HartmanFrom: Cong Wang <[email protected]>
[ Upstream commit 0b2c59720e65885a394a017d0cf9cab118914682 ]
The code in l2tp_tunnel_register() is racy in several ways:
1. It modifies the tunnel socket _after_ publishing it.
2. It calls setup_udp_tunnel_sock() on an existing socket without locking.
3. It changes sock lock class on fly, which triggers many syzbot reports.
This patch amends all of them by moving socket initialization code before publishing and under sock lock. As suggested by Jakub, the l2tp lockdep class is not necessary as we can just switch to bh_lock_sock_nested().
--- net/l2tp/l2tp_core.c | 28 ++++++++++++++-------------- 1 file changed, 14 insertions(+), 14 deletions(-)
net/l2tp/l2tp_core.c +14 -14
@@ -1041,7 +1041,7 @@ static int l2tp_xmit_core(struct l2tp_session *session, struct sk_buff *skb, unsIPCB (skb)->flags &= ~(IPSKB_XFRM_TUNNEL_SIZE |IPSKB_XFRM_TRANSFORMED |IPSKB_REROUTED );nf_reset_ct (skb); -bh_lock_sock (sk); +bh_lock_sock_nested (sk);if (sock_owned_by_user (sk)) {kfree_skb (skb); ret =NET_XMIT_DROP ;
@@ -1387,8 +1387,6 @@ static int l2tp_tunnel_sock_create(struct net *net,return err; } -static struct lock_class_key l2tp_socket_class; -int l2tp_tunnel_create (int fd,int version,u32 tunnel_id,u32 peer_tunnel_id,struct l2tp_tunnel_cfg *cfg,struct l2tp_tunnel **tunnelp) {
@@ -1484,21 +1482,16 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net, } sk = sock->sk; +lock_sock (sk);write_lock_bh (&sk->sk_callback_lock); ret =l2tp_validate_socket (sk, net, tunnel->encap); -if (ret <0 ) +if (ret <0 ) { +release_sock (sk); goto err_inval_sock; + }rcu_assign_sk_user_data (sk, tunnel);write_unlock_bh (&sk->sk_callback_lock); -sock_hold (sk); - tunnel->sock = sk; - tunnel->l2tp_net = net; - -spin_lock_bh (&pn->l2tp_tunnel_idr_lock); -idr_replace (&pn->l2tp_tunnel_idr, tunnel, tunnel->tunnel_id); -spin_unlock_bh (&pn->l2tp_tunnel_idr_lock); -if (tunnel->encap ==L2TP_ENCAPTYPE_UDP ) {struct udp_tunnel_sock_cfg udp_cfg = { .sk_user_data = tunnel,
@@ -1512,9 +1505,16 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net, tunnel->old_sk_destruct = sk->sk_destruct; sk->sk_destruct = &l2tp_tunnel_destruct; -lockdep_set_class_and_name (&sk->sk_lock.slock, &l2tp_socket_class, -"l2tp_sock" ); sk->sk_allocation =GFP_ATOMIC ; +release_sock (sk); + +sock_hold (sk); + tunnel->sock = sk; + tunnel->l2tp_net = net; + +spin_lock_bh (&pn->l2tp_tunnel_idr_lock); +idr_replace (&pn->l2tp_tunnel_idr, tunnel, tunnel->tunnel_id); +spin_unlock_bh (&pn->l2tp_tunnel_idr_lock);trace_register_tunnel (tunnel);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 55/204 octeontx2-pf: Avoid use of GFP_KERNEL in atomic context
In reply to Greg Kroah-HartmanFrom: Geetha sowjanya <[email protected]>
[ Upstream commit 87b93b678e95c7d93fe6a55b0e0fbda26d8c7760 ]
Using GFP_KERNEL in preemption disable context, causing below warning when CONFIG_DEBUG_ATOMIC_SLEEP is enabled.
[ 32.542271] BUG: sleeping function called from invalid context at include/linux/sched/mm.h:274 [ 32.550883] in_atomic(): 1, irqs_disabled(): 0, non_block: 0, pid: 1, name: swapper/0 [ 32.558707] preempt_count: 1, expected: 0 [ 32.562710] RCU nest depth: 0, expected: 0 [ 32.566800] CPU: 3 PID: 1 Comm: swapper/0 Tainted: G W 6.2.0-rc2-00269-gae9dcb91c606 #7 [ 32.576188] Hardware name: Marvell CN106XX board (DT) [ 32.581232] Call trace: [ 32.583670] dump_backtrace.part.0+0xe0/0xf0 [ 32.587937] show_stack+0x18/0x30 [ 32.591245] dump_stack_lvl+0x68/0x84 [ 32.594900] dump_stack+0x18/0x34 [ 32.598206] __might_resched+0x12c/0x160 [ 32.602122] __might_sleep+0x48/0xa0 [ 32.605689] __kmem_cache_alloc_node+0x2b8/0x2e0 [ 32.610301] __kmalloc+0x58/0x190 [ 32.613610] otx2_sq_aura_pool_init+0x1a8/0x314 [ 32.618134] otx2_open+0x1d4/0x9d0
To avoid use of GFP_ATOMIC for memory allocation, disable preemption after all memory allocation is done.
--- drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c +2 -2
@@ -1316,7 +1316,6 @@ int otx2_sq_aura_pool_init(struct otx2_nic *pfvf)if (err) goto fail; -get_cpu ();/* Allocate pointers and free them to aura/pool */ for (qidx =0 ; qidx < hw->tx_queues; qidx++) { pool_id =otx2_get_pool_idx (pfvf,AURA_NIX_SQ , qidx);
@@ -1334,13 +1333,14 @@ int otx2_sq_aura_pool_init(struct otx2_nic *pfvf) err =otx2_alloc_rbuf (pfvf, pool, &bufptr);if (err) goto err_mem; +get_cpu (); pfvf->hw_ops->aura_freeptr (pfvf, pool_id, bufptr); +put_cpu (); sq->sqb_ptrs[sq->sqb_count++] = (u64 )bufptr; } } err_mem: -put_cpu ();return err ? -ENOMEM :0 ; fail:
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 56/204 net: usb: sr9700: Handle negative len
In reply to Greg Kroah-HartmanFrom: Szymon Heidrich <[email protected]>
[ Upstream commit ecf7cf8efb59789e2b21d2f9ab926142579092b2 ]
Packet len computed as difference of length word extracted from skb data and four may result in a negative value. In such case processing of the buffer should be interrupted rather than setting sr_skb->len to an unexpectedly large value (due to cast from signed to unsigned integer) and passing sr_skb to usbnet_skb_return.
--- drivers/net/usb/sr9700.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/net/usb/sr9700.c +1 -1
@@ -410,7 +410,7 @@ static int sr9700_rx_fixup(struct usbnet *dev, struct sk_buff *skb)/* ignore the CRC length */ len = (skb->data[1 ] | (skb->data[2 ] <<8 )) -4 ; -if (len >ETH_FRAME_LEN || len > skb->len) +if (len >ETH_FRAME_LEN || len > skb->len || len <0 )return 0 ;/* the last packet of current skb */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 57/204 net: mdio: validate parameter addr in mdiobus_get_phy()
In reply to Greg Kroah-HartmanFrom: Heiner Kallweit <[email protected]>
[ Upstream commit 867dbe784c5010a466f00a7d1467c1c5ea569c75 ]
The caller may pass any value as addr, what may result in an out-of-bounds access to array mdio_map. One existing case is stmmac_init_phy() that may pass -1 as addr. Therefore validate addr before using it.
--- drivers/net/phy/mdio_bus.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-)
drivers/net/phy/mdio_bus.c +6 -1
@@ -108,7 +108,12 @@ EXPORT_SYMBOL(mdiobus_unregister_device);struct phy_device *mdiobus_get_phy (struct mii_bus *bus,int addr) { -struct mdio_device *mdiodev = bus->mdio_map[addr]; +struct mdio_device *mdiodev; + +if (addr <0 || addr >=ARRAY_SIZE (bus->mdio_map)) +return NULL ; + + mdiodev = bus->mdio_map[addr];if (!mdiodev)return NULL ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 58/204 HID: check empty report_list in hid_validate_values()
In reply to Greg Kroah-HartmanFrom: Pietro Borrello <[email protected]>
[ Upstream commit b12fece4c64857e5fab4290bf01b2e0317a88456 ]
Add a check for empty report_list in hid_validate_values(). The missing check causes a type confusion when issuing a list_entry() on an empty report_list.
The problem is caused by the assumption that the device must have valid report_list. While this will be true for all normal HID devices, a suitably malicious device can violate the assumption.
--- drivers/hid/hid-core.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/hid/hid-core.c +2 -2
@@ -988,8 +988,8 @@ struct hid_report *hid_validate_values(struct hid_device *hid,* Validating on id 0 means we should examine the first * report in the list. */ - report =list_entry ( - hid->report_enum[type].report_list.next, + report =list_first_entry_or_null ( + &hid->report_enum[type].report_list, struct hid_report, list); }else { report = hid->report_enum[type].report_id_hash[id];
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 59/204 HID: check empty report_list in bigben_probe()
In reply to Greg Kroah-HartmanFrom: Pietro Borrello <[email protected]>
[ Upstream commit c7bf714f875531f227f2ef1fdcc8f4d44e7c7d9d ]
Add a check for empty report_list in bigben_probe().
The missing check causes a type confusion when issuing a list_entry() on an empty report_list.
The problem is caused by the assumption that the device must have valid report_list. While this will be true for all normal HID devices, a suitably malicious device can violate the assumption.
--- drivers/hid/hid-bigbenff.c | 5 +++++ 1 file changed, 5 insertions(+)
drivers/hid/hid-bigbenff.c +5 -0
@@ -344,6 +344,11 @@ static int bigben_probe(struct hid_device *hid, } report_list = &hid->report_enum[HID_OUTPUT_REPORT ].report_list; +if (list_empty (report_list)) { +hid_err (hid,"no output report found\n" ); + error = -ENODEV ; + goto error_hw_stop; + } bigben->report =list_entry (report_list->next, struct hid_report, list);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 60/204 net: stmmac: fix invalid call to mdiobus_get_phy()
In reply to Greg Kroah-HartmanFrom: Heiner Kallweit <[email protected]>
[ Upstream commit 1f3bd64ad921f051254591fbed04fd30b306cde6 ]
In a number of cases the driver assigns a default value of -1 to priv->plat->phy_addr. This may result in calling mdiobus_get_phy() with addr parameter being -1. Therefore check for this scenario and bail out before calling mdiobus_get_phy().
--- drivers/net/ethernet/stmicro/stmmac/stmmac_main.c | 5 +++++ 1 file changed, 5 insertions(+)
drivers/net/ethernet/stmicro/stmmac/stmmac_main.c +5 -0
@@ -1242,6 +1242,11 @@ static int stmmac_init_phy(struct net_device *dev)int addr = priv->plat->phy_addr;struct phy_device *phydev; +if (addr <0 ) { +netdev_err (priv->dev,"no phy found\n" ); +return -ENODEV ; + } + phydev =mdiobus_get_phy (priv->mii, addr);if (!phydev) {netdev_err (priv->dev,"no phy at addr %d\n" , addr);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 61/204 pinctrl: rockchip: fix mux route data for rk3568
In reply to Greg Kroah-HartmanFrom: Jonas Karlman <[email protected]>
[ Upstream commit 431d1531466033909d2e8c754a7dc3704b70843f ]
IO mux selection is configured in PMU_GRF_SOC_CON4 and GRF_IOFUNC_SEL0-5 regs on RK3568. pwm0-2 is configured in PMU_GRF reg and the rest is configured in GRF_IOFUNC regs according to TRM [1].
Update mux route data to reflect this and use proper detection pin for UART1 IO mux M1.
This fixes HDMITX IO mux M1 selection and makes it possible to enable HDMI CEC on my Radxa ROCK 3 Model A v1.31 board.
[1] http://opensource.rock-chips.com/images/2/26/Rockchip_RK3568_TRM_Part1_V1.3-20220930P.PDF
--- drivers/pinctrl/pinctrl-rockchip.c | 20 ++++++++++---------- 1 file changed, 10 insertions(+), 10 deletions(-)
drivers/pinctrl/pinctrl-rockchip.c +10 -10
@@ -758,19 +758,19 @@ static struct rockchip_mux_route_data rk3568_mux_route_data[] = {RK_MUXROUTE_PMU (0 ,RK_PB5 ,4 ,0x0110 ,WRITE_MASK_VAL (3 ,2 ,1 )),/* PWM1 IO mux M1 */ RK_MUXROUTE_PMU (0 ,RK_PC1 ,1 ,0x0110 ,WRITE_MASK_VAL (5 ,4 ,0 )),/* PWM2 IO mux M0 */ RK_MUXROUTE_PMU (0 ,RK_PB6 ,4 ,0x0110 ,WRITE_MASK_VAL (5 ,4 ,1 )),/* PWM2 IO mux M1 */ -RK_MUXROUTE_PMU (0 ,RK_PB3 ,2 ,0x0300 ,WRITE_MASK_VAL (0 ,0 ,0 )),/* CAN0 IO mux M0 */ +RK_MUXROUTE_GRF (0 ,RK_PB3 ,2 ,0x0300 ,WRITE_MASK_VAL (0 ,0 ,0 )),/* CAN0 IO mux M0 */ RK_MUXROUTE_GRF (2 ,RK_PA1 ,4 ,0x0300 ,WRITE_MASK_VAL (0 ,0 ,1 )),/* CAN0 IO mux M1 */ RK_MUXROUTE_GRF (1 ,RK_PA1 ,3 ,0x0300 ,WRITE_MASK_VAL (2 ,2 ,0 )),/* CAN1 IO mux M0 */ RK_MUXROUTE_GRF (4 ,RK_PC3 ,3 ,0x0300 ,WRITE_MASK_VAL (2 ,2 ,1 )),/* CAN1 IO mux M1 */ RK_MUXROUTE_GRF (4 ,RK_PB5 ,3 ,0x0300 ,WRITE_MASK_VAL (4 ,4 ,0 )),/* CAN2 IO mux M0 */ RK_MUXROUTE_GRF (2 ,RK_PB2 ,4 ,0x0300 ,WRITE_MASK_VAL (4 ,4 ,1 )),/* CAN2 IO mux M1 */ RK_MUXROUTE_GRF (4 ,RK_PC4 ,1 ,0x0300 ,WRITE_MASK_VAL (6 ,6 ,0 )),/* HPDIN IO mux M0 */ -RK_MUXROUTE_PMU (0 ,RK_PC2 ,2 ,0x0300 ,WRITE_MASK_VAL (6 ,6 ,1 )),/* HPDIN IO mux M1 */ +RK_MUXROUTE_GRF (0 ,RK_PC2 ,2 ,0x0300 ,WRITE_MASK_VAL (6 ,6 ,1 )),/* HPDIN IO mux M1 */ RK_MUXROUTE_GRF (3 ,RK_PB1 ,3 ,0x0300 ,WRITE_MASK_VAL (8 ,8 ,0 )),/* GMAC1 IO mux M0 */ RK_MUXROUTE_GRF (4 ,RK_PA7 ,3 ,0x0300 ,WRITE_MASK_VAL (8 ,8 ,1 )),/* GMAC1 IO mux M1 */ RK_MUXROUTE_GRF (4 ,RK_PD1 ,1 ,0x0300 ,WRITE_MASK_VAL (10 ,10 ,0 )),/* HDMITX IO mux M0 */ -RK_MUXROUTE_PMU (0 ,RK_PC7 ,1 ,0x0300 ,WRITE_MASK_VAL (10 ,10 ,1 )),/* HDMITX IO mux M1 */ -RK_MUXROUTE_PMU (0 ,RK_PB6 ,1 ,0x0300 ,WRITE_MASK_VAL (14 ,14 ,0 )),/* I2C2 IO mux M0 */ +RK_MUXROUTE_GRF (0 ,RK_PC7 ,1 ,0x0300 ,WRITE_MASK_VAL (10 ,10 ,1 )),/* HDMITX IO mux M1 */ +RK_MUXROUTE_GRF (0 ,RK_PB6 ,1 ,0x0300 ,WRITE_MASK_VAL (14 ,14 ,0 )),/* I2C2 IO mux M0 */ RK_MUXROUTE_GRF (4 ,RK_PB4 ,1 ,0x0300 ,WRITE_MASK_VAL (14 ,14 ,1 )),/* I2C2 IO mux M1 */ RK_MUXROUTE_GRF (1 ,RK_PA0 ,1 ,0x0304 ,WRITE_MASK_VAL (0 ,0 ,0 )),/* I2C3 IO mux M0 */ RK_MUXROUTE_GRF(3, RK_PB6, 4, 0x0304, WRITE_MASK_VAL(0, 0, 1)), /* I2C3 IO mux M1 */
@@ -796,7 +796,7 @@ static struct rockchip_mux_route_data rk3568_mux_route_data[] = {RK_MUXROUTE_GRF (4 ,RK_PC3 ,1 ,0x0308 ,WRITE_MASK_VAL (12 ,12 ,1 )),/* PWM15 IO mux M1 */ RK_MUXROUTE_GRF (3 ,RK_PD2 ,3 ,0x0308 ,WRITE_MASK_VAL (14 ,14 ,0 )),/* SDMMC2 IO mux M0 */ RK_MUXROUTE_GRF (3 ,RK_PA5 ,5 ,0x0308 ,WRITE_MASK_VAL (14 ,14 ,1 )),/* SDMMC2 IO mux M1 */ -RK_MUXROUTE_PMU (0 ,RK_PB5 ,2 ,0x030c ,WRITE_MASK_VAL (0 ,0 ,0 )),/* SPI0 IO mux M0 */ +RK_MUXROUTE_GRF (0 ,RK_PB5 ,2 ,0x030c ,WRITE_MASK_VAL (0 ,0 ,0 )),/* SPI0 IO mux M0 */ RK_MUXROUTE_GRF (2 ,RK_PD3 ,3 ,0x030c ,WRITE_MASK_VAL (0 ,0 ,1 )),/* SPI0 IO mux M1 */ RK_MUXROUTE_GRF (2 ,RK_PB5 ,3 ,0x030c ,WRITE_MASK_VAL (2 ,2 ,0 )),/* SPI1 IO mux M0 */ RK_MUXROUTE_GRF(3, RK_PC3, 3, 0x030c, WRITE_MASK_VAL(2, 2, 1)), /* SPI1 IO mux M1 */
@@ -805,8 +805,8 @@ static struct rockchip_mux_route_data rk3568_mux_route_data[] = {RK_MUXROUTE_GRF (4 ,RK_PB3 ,4 ,0x030c ,WRITE_MASK_VAL (6 ,6 ,0 )),/* SPI3 IO mux M0 */ RK_MUXROUTE_GRF (4 ,RK_PC2 ,2 ,0x030c ,WRITE_MASK_VAL (6 ,6 ,1 )),/* SPI3 IO mux M1 */ RK_MUXROUTE_GRF (2 ,RK_PB4 ,2 ,0x030c ,WRITE_MASK_VAL (8 ,8 ,0 )),/* UART1 IO mux M0 */ -RK_MUXROUTE_PMU (0 ,RK_PD1 ,1 ,0x030c ,WRITE_MASK_VAL (8 ,8 ,1 )),/* UART1 IO mux M1 */ -RK_MUXROUTE_PMU (0 ,RK_PD1 ,1 ,0x030c ,WRITE_MASK_VAL (10 ,10 ,0 )),/* UART2 IO mux M0 */ +RK_MUXROUTE_GRF (3 ,RK_PD6 ,4 ,0x030c ,WRITE_MASK_VAL (8 ,8 ,1 )),/* UART1 IO mux M1 */ +RK_MUXROUTE_GRF (0 ,RK_PD1 ,1 ,0x030c ,WRITE_MASK_VAL (10 ,10 ,0 )),/* UART2 IO mux M0 */ RK_MUXROUTE_GRF (1 ,RK_PD5 ,2 ,0x030c ,WRITE_MASK_VAL (10 ,10 ,1 )),/* UART2 IO mux M1 */ RK_MUXROUTE_GRF (1 ,RK_PA1 ,2 ,0x030c ,WRITE_MASK_VAL (12 ,12 ,0 )),/* UART3 IO mux M0 */ RK_MUXROUTE_GRF(3, RK_PB7, 4, 0x030c, WRITE_MASK_VAL(12, 12, 1)), /* UART3 IO mux M1 */
@@ -836,13 +836,13 @@ static struct rockchip_mux_route_data rk3568_mux_route_data[] = {RK_MUXROUTE_GRF (3 ,RK_PD6 ,5 ,0x0314 ,WRITE_MASK_VAL (1 ,0 ,1 )),/* PDM IO mux M1 */ RK_MUXROUTE_GRF (4 ,RK_PA0 ,4 ,0x0314 ,WRITE_MASK_VAL (1 ,0 ,1 )),/* PDM IO mux M1 */ RK_MUXROUTE_GRF (3 ,RK_PC4 ,5 ,0x0314 ,WRITE_MASK_VAL (1 ,0 ,2 )),/* PDM IO mux M2 */ -RK_MUXROUTE_PMU (0 ,RK_PA5 ,3 ,0x0314 ,WRITE_MASK_VAL (3 ,2 ,0 )),/* PCIE20 IO mux M0 */ +RK_MUXROUTE_GRF (0 ,RK_PA5 ,3 ,0x0314 ,WRITE_MASK_VAL (3 ,2 ,0 )),/* PCIE20 IO mux M0 */ RK_MUXROUTE_GRF (2 ,RK_PD0 ,4 ,0x0314 ,WRITE_MASK_VAL (3 ,2 ,1 )),/* PCIE20 IO mux M1 */ RK_MUXROUTE_GRF (1 ,RK_PB0 ,4 ,0x0314 ,WRITE_MASK_VAL (3 ,2 ,2 )),/* PCIE20 IO mux M2 */ -RK_MUXROUTE_PMU (0 ,RK_PA4 ,3 ,0x0314 ,WRITE_MASK_VAL (5 ,4 ,0 )),/* PCIE30X1 IO mux M0 */ +RK_MUXROUTE_GRF (0 ,RK_PA4 ,3 ,0x0314 ,WRITE_MASK_VAL (5 ,4 ,0 )),/* PCIE30X1 IO mux M0 */ RK_MUXROUTE_GRF (2 ,RK_PD2 ,4 ,0x0314 ,WRITE_MASK_VAL (5 ,4 ,1 )),/* PCIE30X1 IO mux M1 */ RK_MUXROUTE_GRF (1 ,RK_PA5 ,4 ,0x0314 ,WRITE_MASK_VAL (5 ,4 ,2 )),/* PCIE30X1 IO mux M2 */ -RK_MUXROUTE_PMU (0 ,RK_PA6 ,2 ,0x0314 ,WRITE_MASK_VAL (7 ,6 ,0 )),/* PCIE30X2 IO mux M0 */ +RK_MUXROUTE_GRF (0 ,RK_PA6 ,2 ,0x0314 ,WRITE_MASK_VAL (7 ,6 ,0 )),/* PCIE30X2 IO mux M0 */ RK_MUXROUTE_GRF (2 ,RK_PD4 ,4 ,0x0314 ,WRITE_MASK_VAL (7 ,6 ,1 )),/* PCIE30X2 IO mux M1 */ RK_MUXROUTE_GRF(4, RK_PC2, 4, 0x0314, WRITE_MASK_VAL(7, 6, 2)), /* PCIE30X2 IO mux M2 */ };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 62/204 HID: revert CHERRY_MOUSE_000C quirk
In reply to Greg Kroah-HartmanFrom: Jiri Kosina <[email protected]>
[ Upstream commit cbf44580ce6b310272a73e3e794233fd064330bd ]
This partially reverts commit f6d910a89a2391 ("HID: usbhid: Add ALWAYS_POLL quirk for some mice"), as it turns out to break reboot on some platforms for reason yet to be understood.
--- drivers/hid/hid-ids.h | 1 - drivers/hid/hid-quirks.c | 1 - 2 files changed, 2 deletions(-)
drivers/hid/hid-ids.h +0 -1
@@ -261,7 +261,6 @@#define USB_DEVICE_ID_CH_AXIS_295 0x001c#define USB_VENDOR_ID_CHERRY 0x046a -#define USB_DEVICE_ID_CHERRY_MOUSE_000C 0x000c#define USB_DEVICE_ID_CHERRY_CYMOTION 0x0023#define USB_DEVICE_ID_CHERRY_CYMOTION_SOLAR 0x0027
drivers/hid/hid-quirks.c +0 -1
@@ -54,7 +54,6 @@ static const struct hid_device_id hid_quirks[] = { { HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_FLIGHT_SIM_YOKE), HID_QUIRK_NOGET }, { HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_PRO_PEDALS), HID_QUIRK_NOGET }, { HID_USB_DEVICE(USB_VENDOR_ID_CH, USB_DEVICE_ID_CH_PRO_THROTTLE), HID_QUIRK_NOGET }, - { HID_USB_DEVICE(USB_VENDOR_ID_CHERRY, USB_DEVICE_ID_CHERRY_MOUSE_000C), HID_QUIRK_ALWAYS_POLL }, { HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K65RGB), HID_QUIRK_NO_INIT_REPORTS }, { HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K65RGB_RAPIDFIRE), HID_QUIRK_NO_INIT_REPORTS | HID_QUIRK_ALWAYS_POLL }, { HID_USB_DEVICE(USB_VENDOR_ID_CORSAIR, USB_DEVICE_ID_CORSAIR_K70RGB), HID_QUIRK_NO_INIT_REPORTS },
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 63/204 usb: gadget: f_fs: Prevent race during ffs_ep0_queue_wait
In reply to Greg Kroah-HartmanFrom: Udipto Goswami <[email protected]>
[ Upstream commit 6a19da111057f69214b97c62fb0ac59023970850 ]
While performing fast composition switch, there is a possibility that the process of ffs_ep0_write/ffs_ep0_read get into a race condition due to ep0req being freed up from functionfs_unbind.
Consider the scenario that the ffs_ep0_write calls the ffs_ep0_queue_wait by taking a lock &ffs->ev.waitq.lock. However, the functionfs_unbind isn't bounded so it can go ahead and mark the ep0req to NULL, and since there is no NULL check in ffs_ep0_queue_wait we will end up in use-after-free.
Fix this by making a serialized execution between the two functions using a mutex_lock(ffs->mutex).
--- drivers/usb/gadget/function/f_fs.c | 5 +++++ 1 file changed, 5 insertions(+)
drivers/usb/gadget/function/f_fs.c +5 -0
@@ -279,6 +279,9 @@ static int __ffs_ep0_queue_wait(struct ffs_data *ffs, char *data, size_t len)struct usb_request *req = ffs->ep0req;int ret; +if (!req) +return -EINVAL ; + req->zero = len <le16_to_cpu (ffs->ev.setup.wLength);spin_unlock_irq (&ffs->ev.waitq.lock);
@@ -1892,10 +1895,12 @@ static void functionfs_unbind(struct ffs_data *ffs)ENTER ();if (!WARN_ON (!ffs->gadget)) { +mutex_lock (&ffs->mutex);usb_ep_free_request (ffs->gadget->ep0, ffs->ep0req); ffs->ep0req =NULL ; ffs->gadget =NULL ;clear_bit (FFS_FL_BOUND , &ffs->flags); +mutex_unlock (&ffs->mutex);ffs_data_put (ffs); } }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 64/204 usb: gadget: f_fs: Ensure ep0req is dequeued before free_request
In reply to Greg Kroah-HartmanFrom: Udipto Goswami <[email protected]>
[ Upstream commit ce405d561b020e5a46340eb5146805a625dcacee ]
As per the documentation, function usb_ep_free_request guarantees the request will not be queued or no longer be re-queued (or otherwise used). However, with the current implementation it doesn't make sure that the request in ep0 isn't reused.
Fix this by dequeuing the ep0req on functionfs_unbind before freeing the request to align with the definition.
--- drivers/usb/gadget/function/f_fs.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/usb/gadget/function/f_fs.c +2 -0
@@ -1895,6 +1895,8 @@ static void functionfs_unbind(struct ffs_data *ffs)ENTER ();if (!WARN_ON (!ffs->gadget)) { +/* dequeue before freeing ep0req */ +usb_ep_dequeue (ffs->gadget->ep0, ffs->ep0req);mutex_lock (&ffs->mutex);usb_ep_free_request (ffs->gadget->ep0, ffs->ep0req); ffs->ep0req =NULL ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 65/204 Bluetooth: Fix possible deadlock in rfcomm_sk_state_change
In reply to Greg Kroah-HartmanFrom: Ying Hsu <[email protected]>
[ Upstream commit 1d80d57ffcb55488f0ec0b77928d4f82d16b6a90 ]
syzbot reports a possible deadlock in rfcomm_sk_state_change [1]. While rfcomm_sock_connect acquires the sk lock and waits for the rfcomm lock, rfcomm_sock_release could have the rfcomm lock and hit a deadlock for acquiring the sk lock. Here's a simplified flow:
rfcomm_sock_connect:
lock_sock(sk)
rfcomm_dlc_open:
rfcomm_lock()
rfcomm_sock_release:
rfcomm_sock_shutdown:
rfcomm_lock()
__rfcomm_dlc_close:
rfcomm_k_state_change:
lock_sock(sk)This patch drops the sk lock before calling rfcomm_dlc_open to avoid the possible deadlock and holds sk's reference count to prevent use-after-free after rfcomm_dlc_open completes.
--- net/bluetooth/rfcomm/sock.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-)
net/bluetooth/rfcomm/sock.c +6 -1
@@ -391,6 +391,7 @@ static int rfcomm_sock_connect(struct socket *sock, struct sockaddr *addr, int a addr->sa_family != AF_BLUETOOTH)return -EINVAL ; +sock_hold (sk);lock_sock (sk);if (sk->sk_state !=BT_OPEN && sk->sk_state !=BT_BOUND ) {
@@ -410,14 +411,18 @@ static int rfcomm_sock_connect(struct socket *sock, struct sockaddr *addr, int a d->sec_level =rfcomm_pi (sk)->sec_level; d->role_switch =rfcomm_pi (sk)->role_switch; +/* Drop sock lock to avoid potential deadlock with the RFCOMM lock */ +release_sock (sk); err =rfcomm_dlc_open (d, &rfcomm_pi (sk)->src, &sa->rc_bdaddr, sa->rc_channel); -if (!err) +lock_sock (sk); +if (!err && !sock_flag (sk,SOCK_ZAPPED )) err =bt_sock_wait_state (sk,BT_CONNECTED ,sock_sndtimeo (sk, flags &O_NONBLOCK )); done:release_sock (sk); +sock_put (sk);return err; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 66/204 net: ipa: disable ipa interrupt during suspend
In reply to Greg Kroah-HartmanFrom: Caleb Connolly <[email protected]>
[ Upstream commit 9ec9b2a30853ba843b70ea16f196e5fe3327be5f ]
The IPA interrupt can fire when pm_runtime is disabled due to it racing with the PM suspend/resume code. This causes a splat in the interrupt handler when it tries to call pm_runtime_get().
Explicitly disable the interrupt in our ->suspend callback, and re-enable it in ->resume to avoid this. If there is an interrupt pending it will be handled after resuming. The interrupt is a wake_irq, as a result even when disabled if it fires it will cause the system to wake from suspend as well as cancel any suspend transition that may be in progress. If there is an interrupt pending, the ipa_isr_thread handler will be called after resuming.
--- drivers/net/ipa/ipa_interrupt.c | 10 ++++++++++ drivers/net/ipa/ipa_interrupt.h | 16 ++++++++++++++++ drivers/net/ipa/ipa_power.c | 17 +++++++++++++++++ 3 files changed, 43 insertions(+)
drivers/net/ipa/ipa_interrupt.c +10 -0
@@ -122,6 +122,16 @@ static irqreturn_t ipa_isr_thread(int irq, void *dev_id)return IRQ_HANDLED ; } +void ipa_interrupt_irq_disable (struct ipa *ipa) +{ +disable_irq (ipa->interrupt->irq); +} + +void ipa_interrupt_irq_enable (struct ipa *ipa) +{ +enable_irq (ipa->interrupt->irq); +} +/* Common function used to enable/disable TX_SUSPEND for an endpoint */ static void ipa_interrupt_suspend_control (struct ipa_interrupt *interrupt,u32 endpoint_id,bool enable)
drivers/net/ipa/ipa_interrupt.h +16 -0
@@ -85,6 +85,22 @@ void ipa_interrupt_suspend_clear_all(struct ipa_interrupt *interrupt);*/ void ipa_interrupt_simulate_suspend (struct ipa_interrupt *interrupt); +/** +* ipa_interrupt_irq_enable() - Enable IPA interrupts +* @ipa: IPA pointer +* +* This enables the IPA interrupt line +*/ +void ipa_interrupt_irq_enable (struct ipa *ipa); + +/** +* ipa_interrupt_irq_disable() - Disable IPA interrupts +* @ipa: IPA pointer +* +* This disables the IPA interrupt line +*/ +void ipa_interrupt_irq_disable (struct ipa *ipa); +/** * ipa_interrupt_config() - Configure the IPA interrupt framework * @ipa: IPA pointer
drivers/net/ipa/ipa_power.c +17 -0
@@ -277,6 +277,17 @@ static int ipa_suspend(struct device *dev)__set_bit (IPA_POWER_FLAG_SYSTEM , ipa->power->flags); +/* Increment the disable depth to ensure that the IRQ won't +* be re-enabled until the matching _enable call in +* ipa_resume(). We do this to ensure that the interrupt +* handler won't run whilst PM runtime is disabled. +* +* Note that disabling the IRQ is NOT the same as disabling +* irq wake. If wakeup is enabled for the IPA then the IRQ +* will still cause the system to wake up, see irq_set_irq_wake(). +*/ +ipa_interrupt_irq_disable (ipa); +return pm_runtime_force_suspend (dev); }
@@ -289,6 +300,12 @@ static int ipa_resume(struct device *dev)__clear_bit (IPA_POWER_FLAG_SYSTEM , ipa->power->flags); +/* Now that PM runtime is enabled again it's safe +* to turn the IRQ back on and process any data +* that was received during suspend. +*/ +ipa_interrupt_irq_enable (ipa); +return ret; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 67/204 net/mlx5: E-switch, Fix setting of reserved fields on MODIFY_SCHEDULING_ELEMENT
In reply to Greg Kroah-HartmanFrom: Maor Dickman <[email protected]>
[ Upstream commit f51471d1935ce1f504fce6c115ce3bfbc32032b0 ]
According to HW spec element_type, element_attributes and parent_element_id fields should be reserved (0x0) when calling MODIFY_SCHEDULING_ELEMENT command.
This patch remove initialization of these fields when calling the command.
--- .../net/ethernet/mellanox/mlx5/core/esw/qos.c | 18 +++--------------- 1 file changed, 3 insertions(+), 15 deletions(-)
drivers/net/ethernet/mellanox/mlx5/core/esw/qos.c +3 -15
@@ -22,15 +22,13 @@ struct mlx5_esw_rate_group { };static int esw_qos_tsar_config (struct mlx5_core_dev *dev,u32 *sched_ctx, -u32 parent_ix,u32 tsar_ix, -u32 max_rate,u32 bw_share) +u32 tsar_ix,u32 max_rate,u32 bw_share) {u32 bitmask =0 ;if (!MLX5_CAP_GEN (dev, qos) || !MLX5_CAP_QOS (dev, esw_scheduling))return -EOPNOTSUPP ; -MLX5_SET (scheduling_context, sched_ctx, parent_element_id, parent_ix);MLX5_SET (scheduling_context, sched_ctx, max_average_bw, max_rate);MLX5_SET (scheduling_context, sched_ctx, bw_share, bw_share); bitmask |=MODIFY_SCHEDULING_ELEMENT_IN_MODIFY_BITMASK_MAX_AVERAGE_BW ;
@@ -51,7 +49,7 @@ static int esw_qos_group_config(struct mlx5_eswitch *esw, struct mlx5_esw_rate_gint err; err =esw_qos_tsar_config (dev, sched_ctx, - esw->qos.root_tsar_ix, group->tsar_ix, + group->tsar_ix, max_rate, bw_share);if (err)NL_SET_ERR_MSG_MOD (extack,"E-Switch modify group TSAR element failed" );
@@ -67,23 +65,13 @@ static int esw_qos_vport_config(struct mlx5_eswitch *esw, struct netlink_ext_ack *extack) {u32 sched_ctx[MLX5_ST_SZ_DW (scheduling_context)] = {}; -struct mlx5_esw_rate_group *group = vport->qos.group;struct mlx5_core_dev *dev = esw->dev; -u32 parent_tsar_ix; -void *vport_elem;int err;if (!vport->qos.enabled)return -EIO ; - parent_tsar_ix = group ? group->tsar_ix : esw->qos.root_tsar_ix; -MLX5_SET (scheduling_context, sched_ctx, element_type, -SCHEDULING_CONTEXT_ELEMENT_TYPE_VPORT ); - vport_elem =MLX5_ADDR_OF (scheduling_context, sched_ctx, - element_attributes); -MLX5_SET (vport_element, vport_elem, vport_number, vport->vport); - - err =esw_qos_tsar_config (dev, sched_ctx, parent_tsar_ix, vport->qos.esw_tsar_ix, + err =esw_qos_tsar_config (dev, sched_ctx, vport->qos.esw_tsar_ix, max_rate, bw_share);if (err) { esw_warn(esw->dev,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 68/204 net: mlx5: eliminate anonymous module_init & module_exit
In reply to Greg Kroah-HartmanFrom: Randy Dunlap <[email protected]>
[ Upstream commit 2c1e1b949024989e20907b84e11a731a50778416 ]
Eliminate anonymous module_init() and module_exit(), which can lead to confusion or ambiguity when reading System.map, crashes/oops/bugs, or an initcall_debug log.
Give each of these init and exit functions unique driver-specific names to eliminate the anonymous names.
Example 1: (System.map)
ffffffff832fc78c t init
ffffffff832fc79e t init
ffffffff832fc8f8 t init
Example 2: (initcall_debug log)
calling init+0x0/0x12 @ 1
initcall init+0x0/0x12 returned 0 after 15 usecs
calling init+0x0/0x60 @ 1
initcall init+0x0/0x60 returned 0 after 2 usecs
calling init+0x0/0x9a @ 1
initcall init+0x0/0x9a returned 0 after 74 usecs
--- drivers/net/ethernet/mellanox/mlx5/core/main.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
drivers/net/ethernet/mellanox/mlx5/core/main.c +4 -4
@@ -1849,7 +1849,7 @@ static void mlx5_core_verify_params(void) } } -static int __init init (void ) +static int __init mlx5_init (void ) {int err;
@@ -1885,7 +1885,7 @@ static int __init init(void)return err; } -static void __exit cleanup(void) +static void __exit mlx5_cleanup(void) {mlx5e_cleanup ();mlx5_sf_driver_unregister ();
@@ -1893,5 +1893,5 @@ static void __exit cleanup(void)mlx5_unregister_debugfs (); } -module_init (init); -module_exit (cleanup); +module_init (mlx5_init); +module_exit (mlx5_cleanup);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 69/204 drm/panfrost: fix GENERIC_ATOMIC64 dependency
In reply to Greg Kroah-HartmanFrom: Arnd Bergmann <[email protected]>
[ Upstream commit 6437a549ae178a3f5a5c03e983f291ebcdc2bbc7 ]
On ARMv5 and earlier, a randconfig build can still run into
WARNING: unmet direct dependencies detected for IOMMU_IO_PGTABLE_LPAE
Depends on [n]: IOMMU_SUPPORT [=y] && (ARM [=y] || ARM64 || COMPILE_TEST [=y]) && !GENERIC_ATOMIC64 [=y] Selected by [y]:
- DRM_PANFROST [=y] && HAS_IOMEM [=y] && DRM [=y] && (ARM [=y] || ARM64 || COMPILE_TEST [=y] && !GENERIC_ATOMIC64 [=y]) && MMU [=y]
Rework the dependencies to always require a working cmpxchg64.
--- drivers/gpu/drm/panfrost/Kconfig | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/gpu/drm/panfrost/Kconfig +2 -1
@@ -3,7 +3,8 @@ config DRM_PANFROST tristate "Panfrost (DRM support for ARM Mali Midgard/Bifrost GPUs)" depends on DRM - depends on ARM || ARM64 || (COMPILE_TEST && !GENERIC_ATOMIC64) + depends on ARM || ARM64 || COMPILE_TEST + depends on !GENERIC_ATOMIC64 # for IOMMU_IO_PGTABLE_LPAE depends on MMU select DRM_SCHED select IOMMU_SUPPORT
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 70/204 dmaengine: Fix double increment of client_count in dma_chan_get()
In reply to Greg Kroah-HartmanFrom: Koba Ko <[email protected]>
[ Upstream commit f3dc1b3b4750851a94212dba249703dd0e50bb20 ]
The first time dma_chan_get() is called for a channel the channel client_count is incorrectly incremented twice for public channels, first in balance_ref_count(), and again prior to returning. This results in an incorrect client count which will lead to the channel resources not being freed when they should be. A simple
test of repeated module load and unload of async_tx on a Dell Power Edge R7425 also shows this resulting in a kref underflow warning.
[ 124.329662] async_tx: api initialized (async) [ 129.000627] async_tx: api initialized (async) [ 130.047839] ------------[ cut here ]------------ [ 130.052472] refcount_t: underflow; use-after-free. [ 130.057279] WARNING: CPU: 3 PID: 19364 at lib/refcount.c:28 refcount_warn_saturate+0xba/0x110 [ 130.065811] Modules linked in: async_tx(-) rfkill intel_rapl_msr
intel_rapl_common amd64_edac edac_mce_amd ipmi_ssif kvm_amd dcdbas kvm mgag200 drm_shmem_helper acpi_ipmi irqbypass drm_kms_helper ipmi_si syscopyarea sysfillrect rapl pcspkr ipmi_devintf sysimgblt fb_sys_fops k10temp i2c_piix4 ipmi_msghandler acpi_power_meter acpi_cpufreq vfat fat drm fuse xfs libcrc32c sd_mod t10_pi sg ahci crct10dif_pclmul libahci crc32_pclmul crc32c_intel ghash_clmulni_intel igb megaraid_sas i40e libata i2c_algo_bit ccp sp5100_tco dca dm_mirror dm_region_hash dm_log dm_mod [last unloaded: async_tx]
[ 130.117361] CPU: 3 PID: 19364 Comm: modprobe Kdump: loaded Not tainted 5.14.0-185.el9.x86_64 #1 [ 130.126091] Hardware name: Dell Inc. PowerEdge R7425/02MJ3T, BIOS 1.18.0 01/17/2022 [ 130.133806] RIP: 0010:refcount_warn_saturate+0xba/0x110 [ 130.139041] Code: 01 01 e8 6d bd 55 00 0f 0b e9 72 9d 8a 00 80 3d 26 18 9c 01 00 75 85 48 c7 c7 f8 a3 03 9d c6 05 16 18 9c 01 01 e8 4a bd 55 00 <0f> 0b e9 4f 9d 8a 00 80 3d 01 18 9c 01 00 0f 85 5e ff ff ff 48 c7 [ 130.157807] RSP: 0018:ffffbf98898afe68 EFLAGS: 00010286 [ 130.163036] RAX: 0000000000000000 RBX: ffff9da06028e598 RCX: 0000000000000000 [ 130.170172] RDX: ffff9daf9de26480 RSI: ffff9daf9de198a0 RDI: ffff9daf9de198a0 [ 130.177316] RBP: ffff9da7cddf3970 R08: 0000000000000000 R09: 00000000ffff7fff [ 130.184459] R10: ffffbf98898afd00 R11: ffffffff9d9e8c28 R12: ffff9da7cddf1970 [ 130.191596] R13: 0000000000000000 R14: 0000000000000000 R15: 0000000000000000 [ 130.198739] FS: 00007f646435c740(0000) GS:ffff9daf9de00000(0000) knlGS:0000000000000000 [ 130.206832] CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 [ 130.212586] CR2: 00007f6463b214f0 CR3: 00000008ab98c000 CR4: 00000000003506e0 [ 130.219729] Call Trace: [ 130.222192] <TASK> [ 130.224305] dma_chan_put+0x10d/0x110 [ 130.227988] dmaengine_put+0x7a/0xa0 [ 130.231575] __do_sys_delete_module.constprop.0+0x178/0x280 [ 130.237157] ? syscall_trace_enter.constprop.0+0x145/0x1d0 [ 130.242652] do_syscall_64+0x5c/0x90 [ 130.246240] ? exc_page_fault+0x62/0x150 [ 130.250178] entry_SYSCALL_64_after_hwframe+0x63/0xcd [ 130.255243] RIP: 0033:0x7f6463a3f5ab [ 130.258830] Code: 73 01 c3 48 8b 0d 75 a8 1b 00 f7 d8 64 89 01 48 83 c8 ff c3 66 2e 0f 1f 84 00 00 00 00 00 90 f3 0f 1e fa b8 b0 00 00 00 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 8b 0d 45 a8 1b 00 f7 d8 64 89 01 48 [ 130.277591] RSP: 002b:00007fff22f972c8 EFLAGS: 00000206 ORIG_RAX: 00000000000000b0 [ 130.285164] RAX: ffffffffffffffda RBX: 000055b6786edd40 RCX: 00007f6463a3f5ab [ 130.292303] RDX: 0000000000000000 RSI: 0000000000000800 RDI: 000055b6786edda8 [ 130.299443] RBP: 000055b6786edd40 R08: 0000000000000000 R09: 0000000000000000 [ 130.306584] R10: 00007f6463b9eac0 R11: 0000000000000206 R12: 000055b6786edda8 [ 130.313731] R13: 0000000000000000 R14: 000055b6786edda8 R15: 00007fff22f995f8 [ 130.320875] </TASK> [ 130.323081] ---[ end trace eff7156d56b5cf25 ]---
cat /sys/class/dma/dma0chan*/in_use would get the wrong result. 2
2
2
--- drivers/dma/dmaengine.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/dma/dmaengine.c +4 -3
@@ -451,7 +451,8 @@ static int dma_chan_get(struct dma_chan *chan)/* The channel is already in use, update client count */ if (chan->client_count) {__module_get (owner); - goto out; + chan->client_count++; +return 0 ; }if (!try_module_get (owner))
@@ -470,11 +471,11 @@ static int dma_chan_get(struct dma_chan *chan) goto err_out; } + chan->client_count++; +if (!dma_has_cap (DMA_PRIVATE , chan->device->cap_mask))balance_ref_count (chan); -out: - chan->client_count++;return 0 ; err_out:
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 71/204 net: macb: fix PTP TX timestamp failure due to packet padding
In reply to Greg Kroah-HartmanFrom: Robert Hancock <[email protected]>
[ Upstream commit 7b90f5a665acd46efbbfa677a3a3a18d01ad6487 ]
PTP TX timestamp handling was observed to be broken with this driver when using the raw Layer 2 PTP encapsulation. ptp4l was not receiving the expected TX timestamp after transmitting a packet, causing it to enter a failure state.
The problem appears to be due to the way that the driver pads packets which are smaller than the Ethernet minimum of 60 bytes. If headroom space was available in the SKB, this caused the driver to move the data back to utilize it. However, this appears to cause other data references in the SKB to become inconsistent. In particular, this caused the ptp_one_step_sync function to later (in the TX completion path) falsely detect the packet as a one-step SYNC packet, even when it was not, which caused the TX timestamp to not be processed when it should be.
Using the headroom for this purpose seems like an unnecessary complexity as this is not a hot path in the driver, and in most cases it appears that there is sufficient tailroom to not require using the headroom anyway. Remove this usage of headroom to prevent this inconsistency from occurring and causing other problems.
--- drivers/net/ethernet/cadence/macb_main.c | 9 +-------- 1 file changed, 1 insertion(+), 8 deletions(-)
drivers/net/ethernet/cadence/macb_main.c +1 -8
@@ -2154,7 +2154,6 @@ static int macb_pad_and_fcs(struct sk_buff **skb, struct net_device *ndev)bool cloned =skb_cloned (*skb) ||skb_header_cloned (*skb) ||skb_is_nonlinear (*skb);int padlen =ETH_ZLEN - (*skb)->len; -int headroom =skb_headroom (*skb);int tailroom =skb_tailroom (*skb);struct sk_buff *nskb;u32 fcs;
@@ -2168,9 +2167,6 @@ static int macb_pad_and_fcs(struct sk_buff **skb, struct net_device *ndev)/* FCS could be appeded to tailroom. */ if (tailroom >=ETH_FCS_LEN ) goto add_fcs; -/* FCS could be appeded by moving data to headroom. */ -else if (!cloned && headroom + tailroom >=ETH_FCS_LEN ) - padlen =0 ;/* No room for FCS, need to reallocate skb. */ else padlen =ETH_FCS_LEN ;
@@ -2179,10 +2175,7 @@ static int macb_pad_and_fcs(struct sk_buff **skb, struct net_device *ndev) padlen +=ETH_FCS_LEN ; } -if (!cloned && headroom + tailroom >= padlen) { - (*skb)->data =memmove ((*skb)->head, (*skb)->data, (*skb)->len); -skb_set_tail_pointer (*skb, (*skb)->len); - }else { +if (cloned || tailroom < padlen) { nskb =skb_copy_expand (*skb,0 , padlen,GFP_ATOMIC );if (!nskb)return -ENOMEM ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 72/204 virtio-net: correctly enable callback during start_xmit
In reply to Greg Kroah-HartmanFrom: Jason Wang <[email protected]>
[ Upstream commit d71ebe8114b4bf622804b810f5e274069060a174 ]
Commit a7766ef18b33("virtio_net: disable cb aggressively") enables virtqueue callback via the following statement:
do {
if (use_napi)
virtqueue_disable_cb(sq->vq);
free_old_xmit_skbs(sq, false);
} while (use_napi && kick &&
unlikely(!virtqueue_enable_cb_delayed(sq->vq)));When NAPI is used and kick is false, the callback won't be enabled here. And when the virtqueue is about to be full, the tx will be disabled, but we still don't enable tx interrupt which will cause a TX hang. This could be observed when using pktgen with burst enabled.
TO be consistent with the logic that tries to disable cb only for NAPI, fixing this by trying to enable delayed callback only when NAPI is enabled when the queue is about to be full.
--- drivers/net/virtio_net.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
drivers/net/virtio_net.c +4 -2
@@ -1780,8 +1780,10 @@ static netdev_tx_t start_xmit(struct sk_buff *skb, struct net_device *dev)*/ if (sq->vq->num_free <2 +MAX_SKB_FRAGS ) {netif_stop_subqueue (dev, qnum); -if (!use_napi && -unlikely (!virtqueue_enable_cb_delayed (sq->vq))) { +if (use_napi) { +if (unlikely (!virtqueue_enable_cb_delayed (sq->vq))) +virtqueue_napi_schedule (&sq->napi, sq->vq); + }else if (unlikely (!virtqueue_enable_cb_delayed (sq->vq))) {/* More just got used, free them then recheck. */ free_old_xmit_skbs (sq, false);if (sq->vq->num_free >=2 +MAX_SKB_FRAGS ) {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 73/204 l2tp: prevent lockdep issue in l2tp_tunnel_register()
In reply to Greg Kroah-HartmanFrom: Eric Dumazet <[email protected]>
[ Upstream commit b9fb10d131b8c84af9bb14e2078d5c63600c7dea ]
lockdep complains with the following lock/unlock sequence:
lock_sock(sk);
write_lock_bh(&sk->sk_callback_lock);[1] release_sock(sk);
[2] write_unlock_bh(&sk->sk_callback_lock);
We need to swap [1] and [2] to fix this issue.
--- net/l2tp/l2tp_core.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-)
net/l2tp/l2tp_core.c +2 -3
@@ -1485,10 +1485,8 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net,lock_sock (sk);write_lock_bh (&sk->sk_callback_lock); ret =l2tp_validate_socket (sk, net, tunnel->encap); -if (ret <0 ) { -release_sock (sk); +if (ret <0 ) goto err_inval_sock; - }rcu_assign_sk_user_data (sk, tunnel);write_unlock_bh (&sk->sk_callback_lock);
@@ -1525,6 +1523,7 @@ int l2tp_tunnel_register(struct l2tp_tunnel *tunnel, struct net *net, err_inval_sock:write_unlock_bh (&sk->sk_callback_lock); +release_sock (sk);if (tunnel->fd <0 )sock_release (sock);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 74/204 HID: betop: check shape of output reports
In reply to Greg Kroah-HartmanFrom: Pietro Borrello <[email protected]>
[ Upstream commit 3782c0d6edf658b71354a64d60aa7a296188fc90 ]
betopff_init() only checks the total sum of the report counts for each report field to be at least 4, but hid_betopff_play() expects 4 report fields.
A device advertising an output report with one field and 4 report counts would pass the check but crash the kernel with a NULL pointer dereference in hid_betopff_play().
--- drivers/hid/hid-betopff.c | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-)
drivers/hid/hid-betopff.c +9 -8
@@ -60,7 +60,6 @@ static int betopff_init(struct hid_device *hid)struct list_head *report_list = &hid->report_enum[HID_OUTPUT_REPORT ].report_list;struct input_dev *dev; -int field_count =0 ;int error;int i, j;
@@ -86,19 +85,21 @@ static int betopff_init(struct hid_device *hid)* ----------------------------------------- * Do init them with default value. */ +if (report->maxfield <4 ) { +hid_err (hid,"not enough fields in the report: %d\n" , + report->maxfield); +return -ENODEV ; + }for (i =0 ; i < report->maxfield; i++) { +if (report->field[i]->report_count <1 ) { +hid_err (hid,"no values in the field\n" ); +return -ENODEV ; + }for (j =0 ; j < report->field[i]->report_count; j++) { report->field[i]->value[j] =0x00 ; - field_count++; } } -if (field_count <4 ) { -hid_err (hid,"not enough fields in the report: %d\n" , - field_count); -return -ENODEV ; - } - betopff =kzalloc (sizeof (*betopff),GFP_KERNEL );if (!betopff)return -ENOMEM ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 75/204 cifs: fix potential deadlock in cache_refresh_path()
In reply to Greg Kroah-HartmanFrom: Paulo Alcantara <[email protected]>
[ Upstream commit 9fb0db40513e27537fde63287aea920b60557a69 ]
Avoid getting DFS referral from an exclusive lock in cache_refresh_path() because the tcon IPC used for getting the referral could be disconnected and thus causing a deadlock as shown below:
task A task B ====== ====== cifs_demultiplex_thread() dfs_cache_find()
cifs_handle_standard() cache_refresh_path()
reconnect_dfs_server() down_write()
dfs_cache_noreq_find() get_dfs_referral()
down_read() <- deadlock smb2_get_dfs_refer()
SMB2_ioctl()
cifs_send_recv()
compound_send_recv()
wait_for_response()
where task A cannot wake up task B because it is blocked on down_read() due to the exclusive lock held in cache_refresh_path() and therefore not being able to make progress.
--- fs/cifs/dfs_cache.c | 42 +++++++++++++++++++++++------------------- 1 file changed, 23 insertions(+), 19 deletions(-)
fs/cifs/dfs_cache.c +23 -19
@@ -792,26 +792,27 @@ static int get_dfs_referral(const unsigned int xid, struct cifs_ses *ses, const*/ static int cache_refresh_path (const unsigned int xid,struct cifs_ses *ses,const char *path) { -int rc; -struct cache_entry *ce;struct dfs_info3_param *refs =NULL ; +struct cache_entry *ce;int numrefs =0 ; -bool newent = false; +int rc;cifs_dbg (FYI ,"%s: search path: %s\n" , __func__, path); -down_write (&htable_rw_lock); +down_read (&htable_rw_lock); ce =lookup_cache_entry (path); -if (!IS_ERR (ce)) { -if (!cache_entry_expired (ce)) { -dump_ce (ce); -up_write (&htable_rw_lock); -return 0 ; - } - }else { - newent = true; +if (!IS_ERR (ce) && !cache_entry_expired (ce)) { +up_read (&htable_rw_lock); +return 0 ; } +/* +* Unlock shared access as we don't want to hold any locks while getting +* a new referral. The @ses used for performing the I/O could be +* reconnecting and it acquires @htable_rw_lock to look up the dfs cache +* in order to failover -- if necessary. +*/ +up_read (&htable_rw_lock);/* * Either the entry was not found, or it is expired.
@@ -819,19 +820,22 @@ static int cache_refresh_path(const unsigned int xid, struct cifs_ses *ses, cons*/ rc =get_dfs_referral (xid, ses, path, &refs, &numrefs);if (rc) - goto out_unlock; + goto out;dump_refs (refs, numrefs); -if (!newent) { - rc =update_cache_entry_locked (ce, refs, numrefs); - goto out_unlock; +down_write (&htable_rw_lock); +/* Re-check as another task might have it added or refreshed already */ + ce =lookup_cache_entry (path); +if (!IS_ERR (ce)) { +if (cache_entry_expired (ce)) + rc =update_cache_entry_locked (ce, refs, numrefs); + }else { + rc =add_cache_entry_locked (refs, numrefs); } - rc =add_cache_entry_locked (refs, numrefs); - -out_unlock:up_write (&htable_rw_lock); +out:free_dfs_info_array (refs, numrefs);return rc; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 76/204 dmaengine: xilinx_dma: call of_node_put() when breaking out of for_each_child_of_node()
In reply to Greg Kroah-HartmanFrom: Liu Shixin <[email protected]>
[ Upstream commit 596b53ccc36a546ab28e8897315c5b4d1d5a0200 ]
Since for_each_child_of_node() will increase the refcount of node, we need to call of_node_put() manually when breaking out of the iteration.
--- drivers/dma/xilinx/xilinx_dma.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/dma/xilinx/xilinx_dma.c +3 -1
@@ -3138,8 +3138,10 @@ static int xilinx_dma_probe(struct platform_device *pdev)/* Initialize the channels */ for_each_child_of_node (node, child) { err =xilinx_dma_child_probe (xdev, child); -if (err <0 ) +if (err <0 ) { +of_node_put (child); goto error; + } }if (xdev->dma_config->dmatype ==XDMA_TYPE_VDMA ) {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 77/204 phy: phy-can-transceiver: Skip warning if no "max-bitrate"
In reply to Greg Kroah-HartmanFrom: Geert Uytterhoeven <[email protected]>
[ Upstream commit bc30c15f275484f9b9fe27c2fa0895f3022d9943 ]
According to the DT bindings, the "max-bitrate" property is optional. However, when it is not present, a warning is printed.
Fix this by adding a missing check for -EINVAL.
--- drivers/phy/phy-can-transceiver.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
drivers/phy/phy-can-transceiver.c +3 -2
@@ -87,6 +87,7 @@ static int can_transceiver_phy_probe(struct platform_device *pdev)struct gpio_desc *standby_gpio;struct gpio_desc *enable_gpio;u32 max_bitrate =0 ; +int err; can_transceiver_phy =devm_kzalloc (dev,sizeof (struct can_transceiver_phy ),GFP_KERNEL );if (!can_transceiver_phy)
@@ -102,8 +103,8 @@ static int can_transceiver_phy_probe(struct platform_device *pdev)return PTR_ERR (phy); } -device_property_read_u32 (dev,"max-bitrate" , &max_bitrate); -if (!max_bitrate) + err =device_property_read_u32 (dev,"max-bitrate" , &max_bitrate); +if ((err != -EINVAL ) && !max_bitrate)dev_warn (dev,"Invalid value for transceiver max bitrate. Ignoring bitrate limit\n" ); phy->attrs.max_link_rate = max_bitrate;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 78/204 drm/amd/display: fix issues with driver unload
In reply to Greg Kroah-HartmanFrom: Hamza Mahfooz <[email protected]>
[ Upstream commit e433adc60f7f847e734c56246b09291532f29b6d ]
Currently, we run into a number of WARN()s when attempting to unload the amdgpu driver (e.g. using "modprobe -r amdgpu"). These all stem from calling drm_encoder_cleanup() too early. So, to fix this we can stop calling drm_encoder_cleanup() from amdgpu_dm_fini() and instead have it be called from amdgpu_dm_encoder_destroy(). Also, we don't need to free in amdgpu_dm_encoder_destroy() since mst_encoders[] isn't explicitly allocated by the slab allocator.
--- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c | 4 ---- drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c | 1 - 2 files changed, 5 deletions(-)
drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm.c +0 -4
@@ -1688,10 +1688,6 @@ static void amdgpu_dm_fini(struct amdgpu_device *adev) }#endif -for (i =0 ; i < adev->dm.display_indexes_num; i++) { -drm_encoder_cleanup (&adev->dm.mst_encoders[i].base); - } -amdgpu_dm_destroy_drm_device (&adev->dm);#if defined(CONFIG_DRM_AMD_SECURE_DISPLAY )
drivers/gpu/drm/amd/display/amdgpu_dm/amdgpu_dm_mst_types.c +0 -1
@@ -385,7 +385,6 @@ static const struct drm_connector_helper_funcs dm_dp_mst_connector_helper_funcsstatic void amdgpu_dm_encoder_destroy (struct drm_encoder *encoder) {drm_encoder_cleanup (encoder); -kfree (encoder); }static const struct drm_encoder_funcs amdgpu_dm_encoder_funcs = {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 79/204 nvme-pci: fix timeout request state check
In reply to Greg Kroah-HartmanFrom: Keith Busch <[email protected]>
[ Upstream commit 1c5842085851f786eba24a39ecd02650ad892064 ]
Polling the completion can progress the request state to IDLE, either inline with the completion, or through softirq. Either way, the state may not be COMPLETED, so don't check for that. We only care if the state isn't IN_FLIGHT.
This is fixing an issue where the driver aborts an IO that we just completed. Seeing the "aborting" message instead of "polled" is very misleading as to where the timeout problem resides.
--- drivers/nvme/host/pci.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/nvme/host/pci.c +1 -1
@@ -1280,7 +1280,7 @@ static enum blk_eh_timer_return nvme_timeout(struct request *req, bool reserved)else nvme_poll_irqdisable (nvmeq); -if (blk_mq_request_completed (req)) { +if (blk_mq_rq_state (req) !=MQ_RQ_IN_FLIGHT ) {dev_warn (dev->ctrl.device,"I/O %d QID %d timeout, completion polled\n" , req->tag, nvmeq->qid);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 80/204 tcp: avoid the lookup process failing to get sk in ehash table
In reply to Greg Kroah-HartmanFrom: Jason Xing <[email protected]>
[ Upstream commit 3f4ca5fafc08881d7a57daa20449d171f2887043 ]
While one cpu is working on looking up the right socket from ehash table, another cpu is done deleting the request socket and is about to add (or is adding) the big socket from the table. It means that we could miss both of them, even though it has little chance.
Let me draw a call trace map of the server side.
CPU 0 CPU 1
----- -----tcp_v4_rcv() syn_recv_sock()
inet_ehash_insert()
-> sk_nulls_del_node_init_rcu(osk)
__inet_lookup_established()
-> __sk_nulls_add_node_rcu(sk, list)Notice that the CPU 0 is receiving the data after the final ack during 3-way shakehands and CPU 1 is still handling the final ack.
Why could this be a real problem?
This case is happening only when the final ack and the first data receiving by different CPUs. Then the server receiving data with ACK flag tries to search one proper established socket from ehash table, but apparently it fails as my map shows above. After that, the server fetches a listener socket and then sends a RST because it finds a ACK flag in the skb (data), which obeys RST definition in RFC 793.
Besides, Eric pointed out there's one more race condition where it handles tw socket hashdance. Only by adding to the tail of the list before deleting the old one can we avoid the race if the reader has already begun the bucket traversal and it would possibly miss the head.
Many thanks to Eric for great help from beginning to end.
--- net/ipv4/inet_hashtables.c | 17 +++++++++++++++-- net/ipv4/inet_timewait_sock.c | 8 ++++---- 2 files changed, 19 insertions(+), 6 deletions(-)
net/ipv4/inet_hashtables.c +15 -2
@@ -571,8 +571,20 @@ bool inet_ehash_insert(struct sock *sk, struct sock *osk, bool *found_dup_sk)spin_lock (lock);if (osk) {WARN_ON_ONCE (sk->sk_hash != osk->sk_hash); - ret =sk_nulls_del_node_init_rcu (osk); - }else if (found_dup_sk) { + ret =sk_hashed (osk); +if (ret) { +/* Before deleting the node, we insert a new one to make +* sure that the look-up-sk process would not miss either +* of them and that at least one node would exist in ehash +* table all the time. Otherwise there's a tiny chance +* that lookup process could find nothing in ehash table. +*/ +__sk_nulls_add_node_tail_rcu (sk, list); +sk_nulls_del_node_init_rcu (osk); + } + goto unlock; + } +if (found_dup_sk) { *found_dup_sk =inet_ehash_lookup_by_sk (sk, list);if (*found_dup_sk) ret = false;
@@ -581,6 +593,7 @@ bool inet_ehash_insert(struct sock *sk, struct sock *osk, bool *found_dup_sk)if (ret)__sk_nulls_add_node_rcu (sk, list); +unlock:spin_unlock (lock);return ret;
net/ipv4/inet_timewait_sock.c +4 -4
@@ -81,10 +81,10 @@ void inet_twsk_put(struct inet_timewait_sock *tw) }EXPORT_SYMBOL_GPL (inet_twsk_put); -static void inet_twsk_add_node_rcu (struct inet_timewait_sock *tw, -struct hlist_nulls_head *list) +static void inet_twsk_add_node_tail_rcu (struct inet_timewait_sock *tw, +struct hlist_nulls_head *list) { -hlist_nulls_add_head_rcu (&tw->tw_node, list); +hlist_nulls_add_tail_rcu (&tw->tw_node, list); } static void inet_twsk_add_bind_node(struct inet_timewait_sock *tw,
@@ -120,7 +120,7 @@ void inet_twsk_hashdance(struct inet_timewait_sock *tw, struct sock *sk,spin_lock (lock); -inet_twsk_add_node_rcu (tw, &ehead->chain); +inet_twsk_add_node_tail_rcu (tw, &ehead->chain);/* Step 3: Remove SK from hash chain */ if (__sk_nulls_del_node_init_rcu (sk))
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 81/204 octeontx2-pf: Fix the use of GFP_KERNEL in atomic context on rt
In reply to Greg Kroah-HartmanFrom: Kevin Hao <[email protected]>
[ Upstream commit 55ba18dc62deff5910c0fa64486dea1ff20832ff ]
The commit 4af1b64f80fb ("octeontx2-pf: Fix lmtst ID used in aura free") uses the get/put_cpu() to protect the usage of percpu pointer in ->aura_freeptr() callback, but it also unnecessarily disable the preemption for the blockable memory allocation. The commit 87b93b678e95 ("octeontx2-pf: Avoid use of GFP_KERNEL in atomic context") tried to fix these sleep inside atomic warnings. But it only fix the one for the non-rt kernel. For the rt kernel, we still get the similar warnings like below.
BUG: sleeping function called from invalid context at kernel/locking/spinlock_rt.c:46
in_atomic(): 1, irqs_disabled(): 0, non_block: 0, pid: 1, name: swapper/0
preempt_count: 1, expected: 0
RCU nest depth: 0, expected: 0
3 locks held by swapper/0/1:
#0: ffff800009fc5fe8 (rtnl_mutex){+.+.}-{3:3}, at: rtnl_lock+0x24/0x30
#1: ffff000100c276c0 (&mbox->lock){+.+.}-{3:3}, at: otx2_init_hw_resources+0x8c/0x3a4
#2: ffffffbfef6537e0 (&cpu_rcache->lock){+.+.}-{2:2}, at: alloc_iova_fast+0x1ac/0x2ac
Preemption disabled at:
[<ffff800008b1908c>] otx2_rq_aura_pool_init+0x14c/0x284
CPU: 20 PID: 1 Comm: swapper/0 Tainted: G W 6.2.0-rc3-rt1-yocto-preempt-rt #1
Hardware name: Marvell OcteonTX CN96XX board (DT)
Call trace:
dump_backtrace.part.0+0xe8/0xf4
show_stack+0x20/0x30
dump_stack_lvl+0x9c/0xd8
dump_stack+0x18/0x34
__might_resched+0x188/0x224
rt_spin_lock+0x64/0x110
alloc_iova_fast+0x1ac/0x2ac
iommu_dma_alloc_iova+0xd4/0x110
__iommu_dma_map+0x80/0x144
iommu_dma_map_page+0xe8/0x260
dma_map_page_attrs+0xb4/0xc0
__otx2_alloc_rbuf+0x90/0x150
otx2_rq_aura_pool_init+0x1c8/0x284
otx2_init_hw_resources+0xe4/0x3a4
otx2_open+0xf0/0x610
__dev_open+0x104/0x224
__dev_change_flags+0x1e4/0x274
dev_change_flags+0x2c/0x7c
ic_open_devs+0x124/0x2f8
ip_auto_config+0x180/0x42c
do_one_initcall+0x90/0x4dc
do_basic_setup+0x10c/0x14c
kernel_init_freeable+0x10c/0x13c
kernel_init+0x2c/0x140
ret_from_fork+0x10/0x20Of course, we can shuffle the get/put_cpu() to only wrap the invocation of ->aura_freeptr() as what commit 87b93b678e95 does. But there are only two ->aura_freeptr() callbacks, otx2_aura_freeptr() and cn10k_aura_freeptr(). There is no usage of perpcu variable in the otx2_aura_freeptr() at all, so the get/put_cpu() seems redundant to it. We can move the get/put_cpu() into the corresponding callback which really has the percpu variable usage and avoid the sprinkling of get/put_cpu() in several places.
--- .../net/ethernet/marvell/octeontx2/nic/otx2_common.c | 11 ++--------- .../net/ethernet/marvell/octeontx2/nic/otx2_common.h | 2 ++ 2 files changed, 4 insertions(+), 9 deletions(-)
drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.c +2 -9
@@ -962,7 +962,6 @@ static void otx2_pool_refill_task(struct work_struct *work) rbpool = cq->rbpool; free_ptrs = cq->pool_ptrs; -get_cpu ();while (cq->pool_ptrs) {if (otx2_alloc_rbuf (pfvf, rbpool, &bufptr)) {/* Schedule a WQ if we fails to free atleast half of the
@@ -982,7 +981,6 @@ static void otx2_pool_refill_task(struct work_struct *work) pfvf->hw_ops->aura_freeptr (pfvf, qidx, bufptr +OTX2_HEAD_ROOM ); cq->pool_ptrs--; } -put_cpu (); cq->refill_task_sched = false; }
@@ -1333,9 +1331,7 @@ int otx2_sq_aura_pool_init(struct otx2_nic *pfvf) err =otx2_alloc_rbuf (pfvf, pool, &bufptr);if (err) goto err_mem; -get_cpu (); pfvf->hw_ops->aura_freeptr (pfvf, pool_id, bufptr); -put_cpu (); sq->sqb_ptrs[sq->sqb_count++] = (u64 )bufptr; } }
@@ -1381,21 +1377,18 @@ int otx2_rq_aura_pool_init(struct otx2_nic *pfvf)if (err) goto fail; -get_cpu ();/* Allocate pointers and free them to aura/pool */ for (pool_id =0 ; pool_id < hw->rqpool_cnt; pool_id++) { pool = &pfvf->qset.pool[pool_id];for (ptr =0 ; ptr < num_ptrs; ptr++) { err =otx2_alloc_rbuf (pfvf, pool, &bufptr);if (err) - goto err_mem; +return -ENOMEM ; pfvf->hw_ops->aura_freeptr (pfvf, pool_id, bufptr +OTX2_HEAD_ROOM ); } } -err_mem: -put_cpu (); -return err ? -ENOMEM :0 ; +return 0 ; fail:otx2_mbox_reset (&pfvf->mbox.mbox,0 );otx2_aura_pool_free (pfvf);
drivers/net/ethernet/marvell/octeontx2/nic/otx2_common.h +2 -0
@@ -605,8 +605,10 @@ static inline void cn10k_aura_freeptr(void *dev, int aura, u64 buf)u64 ptrs[2 ]; ptrs[1 ] = buf; +get_cpu ();/* Free only one buffer at time during init and teardown */ __cn10k_aura_freeptr (pfvf, aura, ptrs,2 ); +put_cpu (); }/* Alloc pointer from pool/aura */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 82/204 ptdma: pt_core_execute_cmd() should use spinlock
In reply to Greg Kroah-HartmanFrom: Eric Pilmore <[email protected]>
[ Upstream commit 95e5fda3b5f9ed8239b145da3fa01e641cf5d53c ]
The interrupt handler (pt_core_irq_handler()) of the ptdma driver can be called from interrupt context. The code flow in this function can lead down to pt_core_execute_cmd() which will attempt to grab a mutex, which is not appropriate in interrupt context and ultimately leads to a kernel panic. The fix here changes this mutex to a spinlock, which has been verified to resolve the issue.
--- drivers/dma/ptdma/ptdma-dev.c | 7 ++++--- drivers/dma/ptdma/ptdma.h | 2 +- 2 files changed, 5 insertions(+), 4 deletions(-)
drivers/dma/ptdma/ptdma-dev.c +4 -3
@@ -71,12 +71,13 @@ static int pt_core_execute_cmd(struct ptdma_desc *desc, struct pt_cmd_queue *cmdbool soc =FIELD_GET (DWORD0_SOC , desc->dw0);u8 *q_desc = (u8 *)&cmd_q->qbase[cmd_q->qidx];u32 tail; +unsigned long flags;if (soc) { desc->dw0 |=FIELD_PREP (DWORD0_IOC , desc->dw0); desc->dw0 &= ~DWORD0_SOC ; } -mutex_lock (&cmd_q->q_mutex); +spin_lock_irqsave (&cmd_q->q_lock, flags);/* Copy 32-byte command descriptor to hw queue. */ memcpy (q_desc, desc,32 );
@@ -91,7 +92,7 @@ static int pt_core_execute_cmd(struct ptdma_desc *desc, struct pt_cmd_queue *cmd/* Turn the queue back on using our cached control register */ pt_start_queue (cmd_q); -mutex_unlock (&cmd_q->q_mutex); +spin_unlock_irqrestore (&cmd_q->q_lock, flags);return 0 ; }
@@ -197,7 +198,7 @@ int pt_core_init(struct pt_device *pt) cmd_q->pt = pt; cmd_q->dma_pool = dma_pool; -mutex_init (&cmd_q->q_mutex); +spin_lock_init (&cmd_q->q_lock);/* Page alignment satisfies our needs for N <= 128 */ cmd_q->qsize =Q_SIZE (Q_DESC_SIZE );
drivers/dma/ptdma/ptdma.h +1 -1
@@ -196,7 +196,7 @@ struct pt_cmd_queue {struct ptdma_desc *qbase;/* Aligned queue start address (per requirement) */ -struct mutex q_mutex____cacheline_aligned ; +spinlock_t q_lock____cacheline_aligned ;unsigned int qidx;unsigned int qsize;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 83/204 device property: fix of node refcount leak in fwnode_graph_get_next_endpoint()
In reply to Greg Kroah-HartmanFrom: Yang Yingliang <[email protected]>
[ Upstream commit 39af728649b05e88a2b40e714feeee6451c3f18e ]
The 'parent' returned by fwnode_graph_get_port_parent() with refcount incremented when 'prev' is not NULL, it needs be put when finish using it.
Because the parent is const, introduce a new variable to store the returned fwnode, then put it before returning from fwnode_graph_get_next_endpoint().
--- drivers/base/property.c | 18 ++++++++++++------ 1 file changed, 12 insertions(+), 6 deletions(-)
drivers/base/property.c +12 -6
@@ -1055,26 +1055,32 @@ struct fwnode_handle * fwnode_graph_get_next_endpoint(const struct fwnode_handle *fwnode, struct fwnode_handle *prev) { + struct fwnode_handle *ep, *port_parent = NULL;const struct fwnode_handle *parent; -struct fwnode_handle *ep;/* * If this function is in a loop and the previous iteration returned * an endpoint from fwnode->secondary, then we need to use the secondary * as parent rather than @fwnode. */ -if (prev) - parent =fwnode_graph_get_port_parent (prev); -else +if (prev) { + port_parent =fwnode_graph_get_port_parent (prev); + parent = port_parent; + }else { parent = fwnode; + }if (IS_ERR_OR_NULL (parent))return NULL ; ep =fwnode_call_ptr_op (parent, graph_get_next_endpoint, prev);if (ep) -return ep; + goto out_put_port_parent; + + ep =fwnode_graph_get_next_endpoint (parent->secondary,NULL ); -return fwnode_graph_get_next_endpoint (parent->secondary,NULL ); +out_put_port_parent: +fwnode_handle_put (port_parent); +return ep; }EXPORT_SYMBOL_GPL (fwnode_graph_get_next_endpoint);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 84/204 w1: fix deadloop in __w1_remove_master_device()
In reply to Greg Kroah-HartmanFrom: Yang Yingliang <[email protected]>
[ Upstream commit 25d5648802f12ae486076ceca5d7ddf1fef792b2 ]
I got a deadloop report while doing device(ds2482) add/remove test:
[ 162.241881] w1_master_driver w1_bus_master1: Waiting for w1_bus_master1 to become free: refcnt=1. [ 163.272251] w1_master_driver w1_bus_master1: Waiting for w1_bus_master1 to become free: refcnt=1. [ 164.296157] w1_master_driver w1_bus_master1: Waiting for w1_bus_master1 to become free: refcnt=1. ...
__w1_remove_master_device() can't return, because the dev->refcnt is not zero.
w1_add_master_device() |
w1_alloc_dev() |
atomic_set(&dev->refcnt, 2) |
kthread_run() |
|__w1_remove_master_device()
| kthread_stop()
// KTHREAD_SHOULD_STOP is set, |
// threadfn(w1_process) won't be |
// called. |
kthread() |
| // refcnt will never be 0, it's deadloop.
| while (atomic_read(&dev->refcnt)) {...}After calling w1_add_master_device(), w1_process() is not really invoked, before w1_process() starting, if kthread_stop() is called in __w1_remove_master_device(), w1_process() will never be called, the refcnt can not be decreased, then it causes deadloop in remove function because of non-zero refcnt.
We need to make sure w1_process() is really started, so move the set refcnt into w1_process() to fix this problem.
--- drivers/w1/w1.c | 2 ++ drivers/w1/w1_int.c | 5 ++--- 2 files changed, 4 insertions(+), 3 deletions(-)
drivers/w1/w1.c +2 -0
@@ -1166,6 +1166,8 @@ int w1_process(void *data)/* remainder if it woke up early */ unsigned long jremain =0 ; +atomic_inc (&dev->refcnt); +for (;;) {if (!jremain && dev->search_count) {
drivers/w1/w1_int.c +2 -3
@@ -51,10 +51,9 @@ static struct w1_master *w1_alloc_dev(u32 id, int slave_count, int slave_ttl, dev->search_count = w1_search_count; dev->enable_pullup = w1_enable_pullup; -/* 1 for w1_process to decrement -* 1 for __w1_remove_master_device to decrement +/* For __w1_remove_master_device to decrement */ -atomic_set (&dev->refcnt,2 ); +atomic_set (&dev->refcnt,1 );INIT_LIST_HEAD (&dev->slist);INIT_LIST_HEAD (&dev->async_list);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 85/204 w1: fix WARNING after calling w1_process()
In reply to Greg Kroah-HartmanFrom: Yang Yingliang <[email protected]>
[ Upstream commit 36225a7c72e9e3e1ce4001b6ce72849f5c9a2d3b ]
I got the following WARNING message while removing driver(ds2482):
------------[ cut here ]------------ do not call blocking ops when !TASK_RUNNING; state=1 set at [<000000002d50bfb6>] w1_process+0x9e/0x1d0 [wire] WARNING: CPU: 0 PID: 262 at kernel/sched/core.c:9817 __might_sleep+0x98/0xa0 CPU: 0 PID: 262 Comm: w1_bus_master1 Tainted: G N 6.1.0-rc3+ #307 RIP: 0010:__might_sleep+0x98/0xa0 Call Trace: exit_signals+0x6c/0x550 do_exit+0x2b4/0x17e0 kthread_exit+0x52/0x60 kthread+0x16d/0x1e0 ret_from_fork+0x1f/0x30
The state of task is set to TASK_INTERRUPTIBLE in loop in w1_process(), set it to TASK_RUNNING when it breaks out of the loop to avoid the warning.
--- drivers/w1/w1.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/w1/w1.c +3 -1
@@ -1195,8 +1195,10 @@ int w1_process(void *data)*/ mutex_unlock (&dev->list_mutex); -if (kthread_should_stop ()) +if (kthread_should_stop ()) { +__set_current_state (TASK_RUNNING );break ; + }/* Only sleep when the search is active. */ if (dev->search_count) {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 86/204 driver core: Fix test_async_probe_init saves device in wrong array
In reply to Greg Kroah-HartmanFrom: Chen Zhongjin <[email protected]>
[ Upstream commit 9be182da0a7526f1b9a3777a336f83baa2e64d23 ]
In test_async_probe_init, second set of asynchronous devices are saved in sync_dev[sync_id], which should be async_dev[async_id]. This makes these devices not unregistered when exit.
Quoted 3 lines
modprobe
test_async_driver_probe&& \
modprobe -rtest_async_driver_probe&& \
modprobetest_async_driver_probe
...
Quoted 2 lines
sysfs: cannot create duplicate filename '/devices/platform/test_async_driver.4'
kobject_add_internalfailed for test_async_driver.4 with-EEXIST,
don't try to register things with the same name in the same directory.
--- drivers/base/test/test_async_driver_probe.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/base/test/test_async_driver_probe.c +1 -1
@@ -146,7 +146,7 @@ static int __init test_async_probe_init(void) calltime =ktime_get ();for_each_online_cpu (cpu) { nid =cpu_to_node (cpu); - pdev = &sync_dev[sync_id]; + pdev = &async_dev[async_id]; *pdev = test_platform_device_register_node("test_async_driver", async_id,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 87/204 selftests/net: toeplitz: fix race on tpacket_v3 block close
In reply to Greg Kroah-HartmanFrom: Willem de Bruijn <[email protected]>
[ Upstream commit 903848249a781d76d59561d51676c95b3a4d7162 ]
Avoid race between process wakeup and tpacket_v3 block timeout.
The test waits for cfg_timeout_msec for packets to arrive. Packets arrive in tpacket_v3 rings, which pass packets ("frames") to the process in batches ("blocks"). The sk waits for req3.tp_retire_blk_tov msec to release a block.
Set the block timeout lower than the process waiting time, else the process may find that no block has been released by the time it scans the socket list. Convert to a ring of more than one, smaller, blocks with shorter timeouts. Blocks must be page aligned, so >= 64KB.
--- tools/testing/selftests/net/toeplitz.c | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-)
tools/testing/selftests/net/toeplitz.c +7 -5
@@ -213,7 +213,7 @@ static char *recv_frame(const struct ring_state *ring, char *frame) }/* A single TPACKET_V3 block can hold multiple frames */ -static void recv_block (struct ring_state *ring) +static bool recv_block (struct ring_state *ring) {struct tpacket_block_desc *block;char *frame;
@@ -221,7 +221,7 @@ static void recv_block(struct ring_state *ring) block = (void *)(ring->mmap + ring->idx * ring_block_sz);if (!(block->hdr.bh1.block_status &TP_STATUS_USER )) -return ; +return false; frame = (char *)block; frame += block->hdr.bh1.offset_to_first_pkt;
@@ -233,6 +233,8 @@ static void recv_block(struct ring_state *ring) block->hdr.bh1.block_status =TP_STATUS_KERNEL ; ring->idx = (ring->idx +1 ) % ring_block_nr; + +return true; }/* simple test: sleep once unconditionally and then process all rings */
@@ -243,7 +245,7 @@ static void process_rings(void)usleep (1000 * cfg_timeout_msec);for (i =0 ; i < num_cpus; i++) -recv_block (&rings[i]); +do {}while (recv_block (&rings[i])); fprintf(stderr, "count: pass=%u nohash=%u fail=%u\n", frames_received - frames_nohash - frames_error,
@@ -255,12 +257,12 @@ static char *setup_ring(int fd)struct tpacket_req3 req3 = {0 };void *ring; - req3.tp_retire_blk_tov = cfg_timeout_msec; + req3.tp_retire_blk_tov = cfg_timeout_msec /8 ; req3.tp_feature_req_word =TP_FT_REQ_FILL_RXHASH ; req3.tp_frame_size =2048 ; req3.tp_frame_nr =1 <<10 ; - req3.tp_block_nr =2 ; + req3.tp_block_nr =16 ; req3.tp_block_size = req3.tp_frame_size * req3.tp_frame_nr; req3.tp_block_size /= req3.tp_block_nr;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 88/204 net: dsa: microchip: ksz9477: port map correction in ALU table entry register
In reply to Greg Kroah-HartmanFrom: Rakesh Sankaranarayanan <[email protected]>
[ Upstream commit 6c977c5c2e4c5d8ad1b604724cc344e38f96fe9b ]
ALU table entry 2 register in KSZ9477 have bit positions reserved for forwarding port map. This field is referred in ksz9477_fdb_del() for clearing forward port map and alu table.
But current fdb_del refer ALU table entry 3 register for accessing forward port map. Update ksz9477_fdb_del() to get forward port map from correct alu table entry register.
With this bug, issue can be observed while deleting static MAC entries. Delete any specific MAC entry using "bridge fdb del" command. This should clear all the specified MAC entries. But it is observed that entries with self static alone are retained.
Tested on LAN9370 EVB since ksz9477_fdb_del() is used common across LAN937x and KSZ series.
--- drivers/net/dsa/microchip/ksz9477.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/net/dsa/microchip/ksz9477.c +2 -2
@@ -675,10 +675,10 @@ static int ksz9477_port_fdb_del(struct dsa_switch *ds, int port,ksz_read32 (dev,REG_SW_ALU_VAL_D , &alu_table[3 ]);/* clear forwarding port */ - alu_table[2 ] &= ~BIT (port); + alu_table[1 ] &= ~BIT (port);/* if there is no port to forward, clear table */ -if ((alu_table[2 ] &ALU_V_PORT_MAP ) ==0 ) { +if ((alu_table[1 ] &ALU_V_PORT_MAP ) ==0 ) { alu_table[0 ] =0 ; alu_table[1 ] =0 ; alu_table[2 ] =0 ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 89/204 thermal/core: Remove duplicate information when an error occurs
In reply to Greg Kroah-HartmanFrom: Daniel Lezcano <[email protected]>
[ Upstream commit 3f95ac324535eafafd436d35bf58f0319dd4a70b ]
The pr_err already tells it is an error, it is pointless to add the 'Error:' string in the messages. Remove them.
Stable-dep-of: 6c54b7bc8a31 ("thermal: core: call put_device() only after device_register() fails")
--- drivers/thermal/thermal_core.c | 8 ++++---- 1 file changed, 4 insertions(+), 4 deletions(-)
drivers/thermal/thermal_core.c +4 -4
@@ -1197,23 +1197,23 @@ thermal_zone_device_register(const char *type, int trips, int mask,struct thermal_governor *governor;if (!type ||strlen (type) ==0 ) { -pr_err ("Error: No thermal zone type defined\n" ); +pr_err ("No thermal zone type defined\n" );return ERR_PTR (-EINVAL ); }if (type &&strlen (type) >=THERMAL_NAME_LENGTH ) { -pr_err ("Error: Thermal zone name (%s) too long, should be under %d chars\n" , +pr_err ("Thermal zone name (%s) too long, should be under %d chars\n" , type,THERMAL_NAME_LENGTH );return ERR_PTR (-EINVAL ); }if (trips >THERMAL_MAX_TRIPS || trips <0 || mask >> trips) { -pr_err ("Error: Incorrect number of thermal trips\n" ); +pr_err ("Incorrect number of thermal trips\n" );return ERR_PTR (-EINVAL ); }if (!ops) { -pr_err ("Error: Thermal zone device ops not defined\n" ); +pr_err ("Thermal zone device ops not defined\n" );return ERR_PTR (-EINVAL ); }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 90/204 thermal/core: Rename trips to num_trips
In reply to Greg Kroah-HartmanFrom: Daniel Lezcano <[email protected]>
[ Upstream commit e5bfcd30f88fdb0ce830229e7ccdeddcb7a59b04 ]
In order to use thermal trips defined in the thermal structure, rename the 'trips' field to 'num_trips' to have the 'trips' field containing the thermal trip points.
Stable-dep-of: 6c54b7bc8a31 ("thermal: core: call put_device() only after device_register() fails")
--- drivers/thermal/gov_fair_share.c | 6 +++--- drivers/thermal/gov_power_allocator.c | 4 ++-- drivers/thermal/tegra/tegra30-tsensor.c | 2 +- drivers/thermal/thermal_core.c | 20 ++++++++++---------- drivers/thermal/thermal_helpers.c | 4 ++-- drivers/thermal/thermal_netlink.c | 2 +- drivers/thermal/thermal_sysfs.c | 22 +++++++++++----------- include/linux/thermal.h | 4 ++-- 8 files changed, 32 insertions(+), 32 deletions(-)
drivers/thermal/gov_fair_share.c +3 -3
@@ -25,10 +25,10 @@ static int get_trip_level(struct thermal_zone_device *tz)int trip_temp;enum thermal_trip_type trip_type; -if (tz->trips ==0 || !tz->ops->get_trip_temp) +if (tz->num_trips ==0 || !tz->ops->get_trip_temp)return 0 ; -for (count =0 ; count < tz->trips; count++) { +for (count =0 ; count < tz->num_trips; count++) { tz->ops->get_trip_temp (tz, count, &trip_temp);if (tz->temperature < trip_temp)break ;
@@ -53,7 +53,7 @@ static long get_target_state(struct thermal_zone_device *tz, cdev->ops->get_max_state (cdev, &max_state); -return (long )(percentage * level * max_state) / (100 * tz->trips); +return (long )(percentage * level * max_state) / (100 * tz->num_trips); }/**
drivers/thermal/gov_power_allocator.c +2 -2
@@ -527,7 +527,7 @@ static void get_governor_trips(struct thermal_zone_device *tz, last_active =INVALID_TRIP ; last_passive =INVALID_TRIP ; -for (i =0 ; i < tz->trips; i++) { +for (i =0 ; i < tz->num_trips; i++) {enum thermal_trip_type type;int ret;
@@ -668,7 +668,7 @@ static int power_allocator_bind(struct thermal_zone_device *tz)get_governor_trips (tz, params); -if (tz->trips >0 ) { +if (tz->num_trips >0 ) { ret = tz->ops->get_trip_temp (tz, params->trip_max_desired_temperature, &control_temp);
drivers/thermal/tegra/tegra30-tsensor.c +1 -1
@@ -316,7 +316,7 @@ static void tegra_tsensor_get_hw_channel_trips(struct thermal_zone_device *tzd, *hot_trip =85000 ; *crit_trip =90000 ; -for (i =0 ; i < tzd->trips; i++) { +for (i =0 ; i < tzd->num_trips; i++) {enum thermal_trip_type type;int trip_temp;
drivers/thermal/thermal_core.c +10 -10
@@ -503,7 +503,7 @@ void thermal_zone_device_update(struct thermal_zone_device *tz, tz->notify_event = event; -for (count =0 ; count < tz->trips; count++) +for (count =0 ; count < tz->num_trips; count++)handle_thermal_trip (tz, count); }EXPORT_SYMBOL_GPL (thermal_zone_device_update);
@@ -628,7 +628,7 @@ int thermal_zone_bind_cooling_device(struct thermal_zone_device *tz,unsigned long max_state;int result, ret; -if (trip >= tz->trips || trip <0 ) +if (trip >= tz->num_trips || trip <0 )return -EINVAL ;list_for_each_entry (pos1, &thermal_tz_list, node) {
@@ -809,7 +809,7 @@ static void __bind(struct thermal_zone_device *tz, int mask, {int i, ret; -for (i =0 ; i < tz->trips; i++) { +for (i =0 ; i < tz->num_trips; i++) {if (mask & (1 << i)) {unsigned long upper, lower;
@@ -1056,7 +1056,7 @@ static void __unbind(struct thermal_zone_device *tz, int mask, {int i; -for (i =0 ; i < tz->trips; i++) +for (i =0 ; i < tz->num_trips; i++)if (mask & (1 << i))thermal_zone_unbind_cooling_device (tz, i, cdev); }
@@ -1161,7 +1161,7 @@ static void bind_tz(struct thermal_zone_device *tz)/** * thermal_zone_device_register() - register a new thermal zone device * @type: the thermal zone device type -* @trips: the number of trip points the thermal zone support +* @num_trips: the number of trip points the thermal zone support * @mask: a bit string indicating the writeablility of trip points * @devdata: private device data * @ops: standard thermal zone device callbacks
@@ -1183,7 +1183,7 @@ static void bind_tz(struct thermal_zone_device *tz)* IS_ERR*() helpers. */ struct thermal_zone_device * -thermal_zone_device_register (const char *type,int trips,int mask, +thermal_zone_device_register (const char *type,int num_trips,int mask,void *devdata,struct thermal_zone_device_ops *ops,struct thermal_zone_params *tzp,int passive_delay,int polling_delay)
@@ -1207,7 +1207,7 @@ thermal_zone_device_register(const char *type, int trips, int mask,return ERR_PTR (-EINVAL ); } -if (trips >THERMAL_MAX_TRIPS || trips <0 || mask >> trips) { +if (num_trips >THERMAL_MAX_TRIPS || num_trips <0 || mask >> num_trips) {pr_err ("Incorrect number of thermal trips\n" );return ERR_PTR (-EINVAL ); }
@@ -1217,7 +1217,7 @@ thermal_zone_device_register(const char *type, int trips, int mask,return ERR_PTR (-EINVAL ); } -if (trips >0 && (!ops->get_trip_type || !ops->get_trip_temp)) +if (num_trips >0 && (!ops->get_trip_type || !ops->get_trip_temp))return ERR_PTR (-EINVAL ); tz =kzalloc (sizeof (*tz),GFP_KERNEL );
@@ -1243,7 +1243,7 @@ thermal_zone_device_register(const char *type, int trips, int mask, tz->tzp = tzp; tz->device.class = &thermal_class; tz->devdata = devdata; - tz->trips = trips; + tz->num_trips = num_trips;thermal_set_delay_jiffies (&tz->passive_delay_jiffies, passive_delay);thermal_set_delay_jiffies (&tz->polling_delay_jiffies, polling_delay);
@@ -1266,7 +1266,7 @@ thermal_zone_device_register(const char *type, int trips, int mask,if (result) goto release_device; -for (count =0 ; count < trips; count++) { +for (count =0 ; count < num_trips; count++) {if (tz->ops->get_trip_type (tz, count, &trip_type) || tz->ops->get_trip_temp (tz, count, &trip_temp) || !trip_temp)
drivers/thermal/thermal_helpers.c +2 -2
@@ -90,7 +90,7 @@ int thermal_zone_get_temp(struct thermal_zone_device *tz, int *temp) ret = tz->ops->get_temp (tz, temp);if (IS_ENABLED (CONFIG_THERMAL_EMULATION ) && tz->emul_temperature) { -for (count =0 ; count < tz->trips; count++) { +for (count =0 ; count < tz->num_trips; count++) { ret = tz->ops->get_trip_type (tz, count, &type);if (!ret && type ==THERMAL_TRIP_CRITICAL ) { ret = tz->ops->get_trip_temp(tz, count,
@@ -138,7 +138,7 @@ void thermal_zone_set_trips(struct thermal_zone_device *tz)if (!tz->ops->set_trips || !tz->ops->get_trip_hyst) goto exit; -for (i =0 ; i < tz->trips; i++) { +for (i =0 ; i < tz->num_trips; i++) {int trip_low; tz->ops->get_trip_temp (tz, i, &trip_temp);
drivers/thermal/thermal_netlink.c +1 -1
@@ -415,7 +415,7 @@ static int thermal_genl_cmd_tz_get_trip(struct param *p)mutex_lock (&tz->lock); -for (i =0 ; i < tz->trips; i++) { +for (i =0 ; i < tz->num_trips; i++) {enum thermal_trip_type type;int temp, hyst =0 ;
drivers/thermal/thermal_sysfs.c +11 -11
@@ -416,15 +416,15 @@ static int create_trip_attrs(struct thermal_zone_device *tz, int mask)int indx;/* This function works only for zones with at least one trip */ -if (tz->trips <=0 ) +if (tz->num_trips <=0 )return -EINVAL ; - tz->trip_type_attrs =kcalloc (tz->trips,sizeof (*tz->trip_type_attrs), + tz->trip_type_attrs =kcalloc (tz->num_trips,sizeof (*tz->trip_type_attrs),GFP_KERNEL );if (!tz->trip_type_attrs)return -ENOMEM ; - tz->trip_temp_attrs =kcalloc (tz->trips,sizeof (*tz->trip_temp_attrs), + tz->trip_temp_attrs =kcalloc (tz->num_trips,sizeof (*tz->trip_temp_attrs),GFP_KERNEL );if (!tz->trip_temp_attrs) {kfree (tz->trip_type_attrs);
@@ -432,7 +432,7 @@ static int create_trip_attrs(struct thermal_zone_device *tz, int mask) }if (tz->ops->get_trip_hyst) { - tz->trip_hyst_attrs =kcalloc (tz->trips, + tz->trip_hyst_attrs =kcalloc (tz->num_trips,sizeof (*tz->trip_hyst_attrs),GFP_KERNEL );if (!tz->trip_hyst_attrs) {
@@ -442,7 +442,7 @@ static int create_trip_attrs(struct thermal_zone_device *tz, int mask) } } - attrs =kcalloc (tz->trips *3 +1 ,sizeof (*attrs),GFP_KERNEL ); + attrs =kcalloc (tz->num_trips *3 +1 ,sizeof (*attrs),GFP_KERNEL );if (!attrs) {kfree (tz->trip_type_attrs);kfree (tz->trip_temp_attrs);
@@ -451,7 +451,7 @@ static int create_trip_attrs(struct thermal_zone_device *tz, int mask)return -ENOMEM ; } -for (indx =0 ; indx < tz->trips; indx++) { +for (indx =0 ; indx < tz->num_trips; indx++) {/* create trip type attribute */ snprintf (tz->trip_type_attrs[indx].name,THERMAL_NAME_LENGTH ,"trip_point_%d_type" , indx);
@@ -478,7 +478,7 @@ static int create_trip_attrs(struct thermal_zone_device *tz, int mask) tz->trip_temp_attrs[indx].attr.store = trip_point_temp_store; } - attrs[indx + tz->trips] = &tz->trip_temp_attrs[indx].attr.attr; + attrs[indx + tz->num_trips] = &tz->trip_temp_attrs[indx].attr.attr;/* create Optional trip hyst attribute */ if (!tz->ops->get_trip_hyst)
@@ -496,10 +496,10 @@ static int create_trip_attrs(struct thermal_zone_device *tz, int mask) tz->trip_hyst_attrs[indx].attr.store = trip_point_hyst_store; } - attrs[indx + tz->trips *2 ] = + attrs[indx + tz->num_trips *2 ] = &tz->trip_hyst_attrs[indx].attr.attr; } - attrs[tz->trips *3 ] =NULL ; + attrs[tz->num_trips *3 ] =NULL ; tz->trips_attribute_group.attrs = attrs;
@@ -540,7 +540,7 @@ int thermal_zone_create_device_groups(struct thermal_zone_device *tz,for (i =0 ; i < size -2 ; i++) groups[i] = thermal_zone_attribute_groups[i]; -if (tz->trips) { +if (tz->num_trips) { result =create_trip_attrs (tz, mask);if (result) {kfree (groups);
@@ -561,7 +561,7 @@ void thermal_zone_destroy_device_groups(struct thermal_zone_device *tz)if (!tz)return ; -if (tz->trips) +if (tz->num_trips)destroy_trip_attrs (tz);kfree (tz->device.groups);
include/linux/thermal.h +2 -2
@@ -113,7 +113,7 @@ struct thermal_cooling_device {* @trip_hyst_attrs: attributes for trip points for sysfs: trip hysteresis * @mode: current mode of this thermal zone * @devdata: private pointer for device private data -* @trips: number of trip points the thermal zone supports +* @num_trips: number of trip points the thermal zone supports * @trips_disabled; bitmap for disabled trips * @passive_delay_jiffies: number of jiffies to wait between polls when * performing passive cooling.
@@ -153,7 +153,7 @@ struct thermal_zone_device {struct thermal_attr *trip_hyst_attrs;enum thermal_device_mode mode;void *devdata; -int trips; +int num_trips;unsigned long trips_disabled;/* bitmap for disabled trips */ unsigned long passive_delay_jiffies;unsigned long polling_delay_jiffies;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 91/204 thermal: Validate new state in cur_state_store()
In reply to Greg Kroah-HartmanFrom: Viresh Kumar <[email protected]>
[ Upstream commit c408b3d1d9bbc7de5fb0304fea424ef2539da616 ]
In cur_state_store(), the new state of the cooling device is received from user-space and is not validated by the thermal core but the same is left for the individual drivers to take care of. Apart from duplicating the code it leaves possibility for introducing bugs where a driver may not do it right.
Lets make the thermal core check the new state itself and store the max value in the cooling device structure.
Stable-dep-of: 6c54b7bc8a31 ("thermal: core: call put_device() only after device_register() fails")
--- drivers/thermal/gov_fair_share.c | 6 +----- drivers/thermal/thermal_core.c | 15 +++++++-------- drivers/thermal/thermal_sysfs.c | 11 +++++------ include/linux/thermal.h | 1 + 4 files changed, 14 insertions(+), 19 deletions(-)
drivers/thermal/gov_fair_share.c +1 -5
@@ -49,11 +49,7 @@ static int get_trip_level(struct thermal_zone_device *tz)static long get_target_state (struct thermal_zone_device *tz,struct thermal_cooling_device *cdev,int percentage,int level) { -unsigned long max_state; - - cdev->ops->get_max_state (cdev, &max_state); - -return (long )(percentage * level * max_state) / (100 * tz->num_trips); +return (long )(percentage * level * cdev->max_state) / (100 * tz->num_trips); }/**
drivers/thermal/thermal_core.c +7 -8
@@ -625,8 +625,7 @@ int thermal_zone_bind_cooling_device(struct thermal_zone_device *tz,struct thermal_instance *pos;struct thermal_zone_device *pos1;struct thermal_cooling_device *pos2; -unsigned long max_state; -int result, ret; +int result;if (trip >= tz->num_trips || trip <0 )return -EINVAL ;
@@ -643,15 +642,11 @@ int thermal_zone_bind_cooling_device(struct thermal_zone_device *tz,if (tz != pos1 || cdev != pos2)return -EINVAL ; - ret = cdev->ops->get_max_state (cdev, &max_state); -if (ret) -return ret; -/* lower default 0, upper default max_state */ lower = lower ==THERMAL_NO_LIMIT ?0 : lower; - upper = upper ==THERMAL_NO_LIMIT ? max_state : upper; + upper = upper ==THERMAL_NO_LIMIT ? cdev->max_state : upper; -if (lower > upper || upper > max_state) +if (lower > upper || upper > cdev->max_state)return -EINVAL ; dev =kzalloc (sizeof (*dev),GFP_KERNEL );
@@ -918,6 +913,10 @@ __thermal_cooling_device_register(struct device_node *np, cdev->updated = false; cdev->device.class = &thermal_class; cdev->devdata = devdata; + +if (cdev->ops->get_max_state (cdev, &cdev->max_state)) + goto out_kfree_type; +thermal_cooling_device_setup_sysfs (cdev); ret =dev_set_name (&cdev->device,"cooling_device%d" , cdev->id);if (ret) {
drivers/thermal/thermal_sysfs.c +5 -6
@@ -580,13 +580,8 @@ static ssize_t max_state_show(struct device *dev, struct device_attribute *attr, char *buf) {struct thermal_cooling_device *cdev =to_cooling_device (dev); -unsigned long state; -int ret; - ret = cdev->ops->get_max_state (cdev, &state); -if (ret) -return ret; -return sprintf (buf,"%ld\n" , state); +return sprintf (buf,"%ld\n" , cdev->max_state); } static ssize_t cur_state_show(struct device *dev, struct device_attribute *attr,
@@ -616,6 +611,10 @@ cur_state_store(struct device *dev, struct device_attribute *attr,if ((long )state <0 )return -EINVAL ; +/* Requested state should be less than max_state + 1 */ +if (state > cdev->max_state) +return -EINVAL ; +mutex_lock (&cdev->lock); result = cdev->ops->set_cur_state (cdev, state);
include/linux/thermal.h +1 -0
@@ -92,6 +92,7 @@ struct thermal_cooling_device_ops {struct thermal_cooling_device {int id;char *type; +unsigned long max_state;struct device device;struct device_node *np;void *devdata;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 92/204 thermal/core: fix error code in __thermal_cooling_device_register()
In reply to Greg Kroah-HartmanFrom: Dan Carpenter <[email protected]>
[ Upstream commit e49a1e1ee078aee21006192076a8d93335e0daa9 ]
Return an error pointer if ->get_max_state() fails. The current code returns NULL which will cause an oops in the callers.
Stable-dep-of: 6c54b7bc8a31 ("thermal: core: call put_device() only after device_register() fails")
--- drivers/thermal/thermal_core.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/thermal/thermal_core.c +2 -1
@@ -914,7 +914,8 @@ __thermal_cooling_device_register(struct device_node *np, cdev->device.class = &thermal_class; cdev->devdata = devdata; -if (cdev->ops->get_max_state (cdev, &cdev->max_state)) + ret = cdev->ops->get_max_state (cdev, &cdev->max_state); +if (ret) goto out_kfree_type;thermal_cooling_device_setup_sysfs (cdev);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 93/204 thermal: core: call put_device() only after device_register() fails
In reply to Greg Kroah-HartmanFrom: Viresh Kumar <[email protected]>
[ Upstream commit 6c54b7bc8a31ce0f7cc7f8deef05067df414f1d8 ]
put_device() shouldn't be called before a prior call to device_register(). __thermal_cooling_device_register() doesn't follow that properly and needs fixing. Also thermal_cooling_device_destroy_sysfs() is getting called unnecessarily on few error paths.
Fix all this by placing the calls at the right place.
Based on initial work done by Caleb Connolly.
--- drivers/thermal/thermal_core.c | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-)
drivers/thermal/thermal_core.c +10 -3
@@ -915,15 +915,20 @@ __thermal_cooling_device_register(struct device_node *np, cdev->devdata = devdata; ret = cdev->ops->get_max_state (cdev, &cdev->max_state); -if (ret) - goto out_kfree_type; +if (ret) { +kfree (cdev->type); + goto out_ida_remove; + }thermal_cooling_device_setup_sysfs (cdev); + ret =dev_set_name (&cdev->device,"cooling_device%d" , cdev->id);if (ret) { +kfree (cdev->type);thermal_cooling_device_destroy_sysfs (cdev); - goto out_kfree_type; + goto out_ida_remove; } + ret =device_register (&cdev->device);if (ret) goto out_kfree_type;
@@ -949,6 +954,8 @@ __thermal_cooling_device_register(struct device_node *np,thermal_cooling_device_destroy_sysfs (cdev);kfree (cdev->type);put_device (&cdev->device); + +/* thermal_release() takes care of the rest */ cdev =NULL ; out_ida_remove:ida_simple_remove (&thermal_cdev_ida, id);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 94/204 net: stmmac: enable all safety features by default
In reply to Greg Kroah-HartmanFrom: Andrew Halaney <[email protected]>
[ Upstream commit fdfc76a116b5e9d3e98e6c96fe83b42d011d21d4 ]
In the original implementation of dwmac5
commit 8bf993a5877e ("net: stmmac: Add support for DWMAC5 and implement Safety Features") all safety features were enabled by default.
Later it seems some implementations didn't have support for all the features, so in
commit 5ac712dcdfef ("net: stmmac: enable platform specific safety features") the safety_feat_cfg structure was added to the callback and defined for some platforms to selectively enable these safety features.
The problem is that only certain platforms were given that software support. If the automotive safety package bit is set in the hardware features register the safety feature callback is called for the platform, and for platforms that didn't get a safety_feat_cfg defined this results in the following NULL pointer dereference:
[ 7.933303] Call trace: [ 7.935812] dwmac5_safety_feat_config+0x20/0x170 [stmmac] [ 7.941455] __stmmac_open+0x16c/0x474 [stmmac] [ 7.946117] stmmac_open+0x38/0x70 [stmmac] [ 7.950414] __dev_open+0x100/0x1dc [ 7.954006] __dev_change_flags+0x18c/0x204 [ 7.958297] dev_change_flags+0x24/0x6c [ 7.962237] do_setlink+0x2b8/0xfa4 [ 7.965827] __rtnl_newlink+0x4ec/0x840 [ 7.969766] rtnl_newlink+0x50/0x80 [ 7.973353] rtnetlink_rcv_msg+0x12c/0x374 [ 7.977557] netlink_rcv_skb+0x5c/0x130 [ 7.981500] rtnetlink_rcv+0x18/0x2c [ 7.985172] netlink_unicast+0x2e8/0x340 [ 7.989197] netlink_sendmsg+0x1a8/0x420 [ 7.993222] ____sys_sendmsg+0x218/0x280 [ 7.997249] ___sys_sendmsg+0xac/0x100 [ 8.001103] __sys_sendmsg+0x84/0xe0 [ 8.004776] __arm64_sys_sendmsg+0x24/0x30 [ 8.008983] invoke_syscall+0x48/0x114 [ 8.012840] el0_svc_common.constprop.0+0xcc/0xec [ 8.017665] do_el0_svc+0x38/0xb0 [ 8.021071] el0_svc+0x2c/0x84 [ 8.024212] el0t_64_sync_handler+0xf4/0x120 [ 8.028598] el0t_64_sync+0x190/0x194
Go back to the original behavior, if the automotive safety package is found to be supported in hardware enable all the features unless safety_feat_cfg is passed in saying this particular platform only supports a subset of the features.
--- drivers/net/ethernet/stmicro/stmmac/dwmac5.c | 14 ++++++++++++++ 1 file changed, 14 insertions(+)
drivers/net/ethernet/stmicro/stmmac/dwmac5.c +14 -0
@@ -186,11 +186,25 @@ static void dwmac5_handle_dma_err(struct net_device *ndev,int dwmac5_safety_feat_config (void __iomem *ioaddr,unsigned int asp,struct stmmac_safety_feature_cfg *safety_feat_cfg) { +struct stmmac_safety_feature_cfg all_safety_feats = { + .tsoee =1 , + .mrxpee =1 , + .mestee =1 , + .mrxee =1 , + .mtxee =1 , + .epsi =1 , + .edpp =1 , + .prtyen =1 , + .tmouten =1 , + };u32 value;if (!asp)return -EINVAL ; +if (!safety_feat_cfg) + safety_feat_cfg = &all_safety_feats; +/* 1. Enable Safety Features */ value =readl (ioaddr +MTL_ECC_CONTROL ); value |=MEEAO ;/* MTL ECC Error Addr Status Override */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 95/204 tcp: fix rate_app_limited to default to 1
In reply to Greg Kroah-HartmanFrom: David Morley <[email protected]>
[ Upstream commit 300b655db1b5152d6101bcb6801d50899b20c2d6 ]
The initial default value of 0 for tp->rate_app_limited was incorrect, since a flow is indeed application-limited until it first sends data. Fixing the default to be 1 is generally correct but also specifically will help user-space applications avoid using the initial tcpi_delivery_rate value of 0 that persists until the connection has some non-zero bandwidth sample.
--- net/ipv4/tcp.c | 2 ++ 1 file changed, 2 insertions(+)
net/ipv4/tcp.c +2 -0
@@ -439,6 +439,7 @@ void tcp_init_sock(struct sock *sk)/* There's a bubble in the pipe until at least the first ACK. */ tp->app_limited = ~0U ; + tp->rate_app_limited =1 ;/* See draft-stevens-tcpca-spec-01 for discussion of the * initialization of these values.
@@ -3066,6 +3067,7 @@ int tcp_disconnect(struct sock *sk, int flags) tp->last_oow_ack_time =0 ;/* There's a bubble in the pipe until at least the first ACK. */ tp->app_limited = ~0U ; + tp->rate_app_limited =1 ; tp->rack.mstamp =0 ; tp->rack.advanced =0 ; tp->rack.reo_wnd_steps =1 ;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 96/204 scsi: iscsi: Fix multiple iSCSI session unbind events sent to userspace
In reply to Greg Kroah-HartmanFrom: Wenchao Hao <[email protected]>
[ Upstream commit a3be19b91ea7121d388084e8c07f5b1b982eb40c ]
It was observed that the kernel would potentially send ISCSI_KEVENT_UNBIND_SESSION multiple times. Introduce 'target_state' in iscsi_cls_session() to make sure session will send only one unbind session event.
This introduces a regression wrt. the issue fixed in commit 13e60d3ba287 ("scsi: iscsi: Report unbind session event when the target has been removed"). If iscsid dies for any reason after sending an unbind session to kernel, once iscsid is restarted, the kernel's ISCSI_KEVENT_UNBIND_SESSION event is lost and userspace is then unable to logout. However, the session is actually in invalid state (its target_id is INVALID) so iscsid should not sync this session during restart.
Consequently we need to check the session's target state during iscsid restart. If session is in unbound state, do not sync this session and perform session teardown. This is OK because once a session is unbound, we can not recover it any more (mainly because its target id is INVALID).
--- drivers/scsi/scsi_transport_iscsi.c | 50 ++++++++++++++++++++++++++--- include/scsi/scsi_transport_iscsi.h | 9 ++++++ 2 files changed, 54 insertions(+), 5 deletions(-)
drivers/scsi/scsi_transport_iscsi.c +45 -5
@@ -1679,6 +1679,13 @@ static const char *iscsi_session_state_name(int state)return name; } +static char *iscsi_session_target_state_name[] = { + [ISCSI_SESSION_TARGET_UNBOUND ] ="UNBOUND" , + [ISCSI_SESSION_TARGET_ALLOCATED ] ="ALLOCATED" , + [ISCSI_SESSION_TARGET_SCANNED ] ="SCANNED" , + [ISCSI_SESSION_TARGET_UNBINDING ] ="UNBINDING" , +}; +int iscsi_session_chkready (struct iscsi_cls_session *session) {int err;
@@ -1807,9 +1814,13 @@ static int iscsi_user_scan_session(struct device *dev, void *data)if ((scan_data->channel ==SCAN_WILD_CARD || scan_data->channel ==0 ) && (scan_data->id ==SCAN_WILD_CARD || - scan_data->id == id)) + scan_data->id == id)) {scsi_scan_target (&session->dev,0 , id, scan_data->lun, scan_data->rescan); +spin_lock_irqsave (&session->lock, flags); + session->target_state =ISCSI_SESSION_TARGET_SCANNED ; +spin_unlock_irqrestore (&session->lock, flags); + } } user_scan_exit:
@@ -1998,31 +2009,41 @@ static void __iscsi_unbind_session(struct work_struct *work)struct iscsi_cls_host *ihost = shost->shost_data;unsigned long flags;unsigned int target_id; +bool remove_target = true;ISCSI_DBG_TRANS_SESSION (session,"Unbinding session\n" );/* Prevent new scans and make sure scanning is not in progress */ mutex_lock (&ihost->mutex);spin_lock_irqsave (&session->lock, flags); -if (session->target_id ==ISCSI_MAX_TARGET ) { +if (session->target_state ==ISCSI_SESSION_TARGET_ALLOCATED ) { + remove_target = false; + }else if (session->target_state !=ISCSI_SESSION_TARGET_SCANNED ) {spin_unlock_irqrestore (&session->lock, flags);mutex_unlock (&ihost->mutex); - goto unbind_session_exit; +ISCSI_DBG_TRANS_SESSION (session, +"Skipping target unbinding: Session is unbound/unbinding.\n" ); +return ; } + session->target_state =ISCSI_SESSION_TARGET_UNBINDING ; target_id = session->target_id; session->target_id =ISCSI_MAX_TARGET ;spin_unlock_irqrestore (&session->lock, flags);mutex_unlock (&ihost->mutex); -scsi_remove_target (&session->dev); +if (remove_target) +scsi_remove_target (&session->dev);if (session->ida_used)ida_simple_remove (&iscsi_sess_ida, target_id); -unbind_session_exit:iscsi_session_event (session,ISCSI_KEVENT_UNBIND_SESSION );ISCSI_DBG_TRANS_SESSION (session,"Completed target removal\n" ); + +spin_lock_irqsave (&session->lock, flags); + session->target_state =ISCSI_SESSION_TARGET_UNBOUND ; +spin_unlock_irqrestore (&session->lock, flags); }static void __iscsi_destroy_session (struct work_struct *work)
@@ -2091,6 +2112,9 @@ int iscsi_add_session(struct iscsi_cls_session *session, unsigned int target_id) session->ida_used = true; }else session->target_id = target_id; +spin_lock_irqsave (&session->lock, flags); + session->target_state =ISCSI_SESSION_TARGET_ALLOCATED ; +spin_unlock_irqrestore (&session->lock, flags);dev_set_name (&session->dev,"session%u" , session->sid); err =device_add (&session->dev);
@@ -4391,6 +4415,19 @@ iscsi_session_attr(def_taskmgmt_tmo, ISCSI_PARAM_DEF_TASKMGMT_TMO, 0);iscsi_session_attr (discovery_parent_idx,ISCSI_PARAM_DISCOVERY_PARENT_IDX ,0 );iscsi_session_attr (discovery_parent_type,ISCSI_PARAM_DISCOVERY_PARENT_TYPE ,0 ); +static ssize_t +show_priv_session_target_state (struct device *dev,struct device_attribute *attr, +char *buf) +{ +struct iscsi_cls_session *session =iscsi_dev_to_session (dev->parent); + +return sysfs_emit (buf,"%s\n" , + iscsi_session_target_state_name[session->target_state]); +} + +static ISCSI_CLASS_ATTR(priv_sess, target_state, S_IRUGO, + show_priv_session_target_state, NULL); +static ssize_t show_priv_session_state (struct device *dev,struct device_attribute *attr,char *buf)
@@ -4493,6 +4530,7 @@ static struct attribute *iscsi_session_attrs[] = { &dev_attr_sess_boot_target.attr, &dev_attr_priv_sess_recovery_tmo.attr, &dev_attr_priv_sess_state.attr, + &dev_attr_priv_sess_target_state.attr, &dev_attr_priv_sess_creator.attr, &dev_attr_sess_chap_out_idx.attr, &dev_attr_sess_chap_in_idx.attr,
@@ -4606,6 +4644,8 @@ static umode_t iscsi_session_attr_is_visible(struct kobject *kobj,return S_IRUGO |S_IWUSR ; else if (attr == &dev_attr_priv_sess_state.attr)return S_IRUGO ; + else if (attr == &dev_attr_priv_sess_target_state.attr) +return S_IRUGO ; else if (attr == &dev_attr_priv_sess_creator.attr)return S_IRUGO ; else if (attr == &dev_attr_priv_sess_target_id.attr)
include/scsi/scsi_transport_iscsi.h +9 -0
@@ -236,6 +236,14 @@ enum { ISCSI_SESSION_FREE, }; +enum { +ISCSI_SESSION_TARGET_UNBOUND , +ISCSI_SESSION_TARGET_ALLOCATED , +ISCSI_SESSION_TARGET_SCANNED , +ISCSI_SESSION_TARGET_UNBINDING , +ISCSI_SESSION_TARGET_MAX , +}; +#define ISCSI_MAX_TARGET -1struct iscsi_cls_session {
@@ -262,6 +270,7 @@ struct iscsi_cls_session {*/ pid_t creator;int state; +int target_state;/* session target bind state */ int sid;/* session id */ void *dd_data;/* LLD private data */ struct device dev;/* sysfs transport/container device */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 97/204 cpufreq: Add Tegra234 to cpufreq-dt-platdev blocklist
In reply to Greg Kroah-HartmanFrom: Sumit Gupta <[email protected]>
[ Upstream commit 01c5bb0cc2a39fbc56ff9a5ef28b79447f0c2351 ]
Tegra234 platform uses the tegra194-cpufreq driver, so add it to the blocklist in cpufreq-dt-platdev driver to avoid the cpufreq driver registration from there.
--- drivers/cpufreq/cpufreq-dt-platdev.c | 1 + 1 file changed, 1 insertion(+)
drivers/cpufreq/cpufreq-dt-platdev.c +1 -0
@@ -133,6 +133,7 @@ static const struct of_device_id blocklist[] __initconst = { { .compatible = "nvidia,tegra30", }, { .compatible = "nvidia,tegra124", }, { .compatible = "nvidia,tegra210", }, + { .compatible = "nvidia,tegra234", }, { .compatible = "qcom,apq8096", }, { .compatible = "qcom,msm8996", },
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 98/204 kcsan: test: dont put the expect array on the stack
In reply to Greg Kroah-HartmanFrom: Max Filippov <[email protected]>
[ Upstream commit 5b24ac2dfd3eb3e36f794af3aa7f2828b19035bd ]
Size of the 'expect' array in the __report_matches is 1536 bytes, which is exactly the default frame size warning limit of the xtensa architecture.
As a result allmodconfig xtensa kernel builds with the gcc that does not support the compiler plugins (which otherwise would push the said warning limit to 2K) fail with the following message:
kernel/kcsan/kcsan_test.c:257:1: error: the frame size of 1680 bytes
is larger than 1536 bytes
Fix it by dynamically allocating the 'expect' array.
--- kernel/kcsan/kcsan_test.c | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-)
kernel/kcsan/kcsan_test.c +6 -1
@@ -151,7 +151,7 @@ static bool report_matches(const struct expect_report *r)const bool is_assert = (r->access[0 ].type | r->access[1 ].type) &KCSAN_ACCESS_ASSERT ;bool ret = false;unsigned long flags; - typeof(observed.lines) expect; +typeof (*observed.lines) *expect;const char *end;char *cur;int i;
@@ -160,6 +160,10 @@ static bool report_matches(const struct expect_report *r)if (!report_available ())return false; + expect =kmalloc (sizeof (observed.lines),GFP_KERNEL ); +if (WARN_ON (!expect)) +return false; +/* Generate expected report contents. */ /* Title */
@@ -243,6 +247,7 @@ static bool report_matches(const struct expect_report *r) strstr(observed.lines[2], expect[1]))); out:spin_unlock_irqrestore (&observed.lock, flags); +kfree (expect);return ret; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 99/204 cpufreq: Add SM6375 to cpufreq-dt-platdev blocklist
In reply to Greg Kroah-HartmanFrom: Konrad Dybcio <[email protected]>
[ Upstream commit faf28e240dd118d9521c68aeb9388b9b8f02d9d0 ]
The Qualcomm SM6375 platform uses the qcom-cpufreq-hw driver, so add it to the cpufreq-dt-platdev driver's blocklist.
--- drivers/cpufreq/cpufreq-dt-platdev.c | 1 + 1 file changed, 1 insertion(+)
drivers/cpufreq/cpufreq-dt-platdev.c +1 -0
@@ -144,6 +144,7 @@ static const struct of_device_id blocklist[] __initconst = { { .compatible = "qcom,sc8180x", }, { .compatible = "qcom,sdm845", }, { .compatible = "qcom,sm6350", }, + { .compatible = "qcom,sm6375", }, { .compatible = "qcom,sm8150", }, { .compatible = "qcom,sm8250", }, { .compatible = "qcom,sm8350", },
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 100/204 ASoC: fsl_micfil: Correct the number of steps on SX controls
In reply to Greg Kroah-HartmanFrom: Chancel Liu <[email protected]>
[ Upstream commit cdfa92eb90f5770b26a79824ef213ebdbbd988b1 ]
The parameter "max" of SOC_SINGLE_SX_TLV() means the number of steps rather than maximum value. This patch corrects the minimum value to -8 and the number of steps to 15.
--- sound/soc/fsl/fsl_micfil.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-)
sound/soc/fsl/fsl_micfil.c +8 -8
@@ -88,21 +88,21 @@ static DECLARE_TLV_DB_SCALE(gain_tlv, 0, 100, 0);static const struct snd_kcontrol_new fsl_micfil_snd_controls[] = {SOC_SINGLE_SX_TLV ("CH0 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (0 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (0 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH1 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (1 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (1 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH2 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (2 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (2 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH3 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (3 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (3 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH4 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (4 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (4 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH5 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (5 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (5 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH6 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (6 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (6 ),0x8 ,0xF , gain_tlv),SOC_SINGLE_SX_TLV ("CH7 Volume" ,REG_MICFIL_OUT_CTRL , -MICFIL_OUTGAIN_CHX_SHIFT (7 ),0xF ,0x7 , gain_tlv), +MICFIL_OUTGAIN_CHX_SHIFT (7 ),0x8 ,0xF , gain_tlv),SOC_ENUM_EXT ("MICFIL Quality Select" , fsl_micfil_quality_enum, snd_soc_get_enum_double, snd_soc_put_enum_double),
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 101/204 net: usb: cdc_ether: add support for Thales Cinterion PLS62-W modem
In reply to Greg Kroah-HartmanFrom: Hui Wang <[email protected]>
[ Upstream commit eea8ce81fbb544e3caad1a1c876ba1af467b3d3c ]
This modem has 7 interfaces, 5 of them are serial interfaces and are driven by cdc_acm, while 2 of them are wwan interfaces and are driven by cdc_ether:
If 0: Abstract (modem)
If 1: Abstract (modem)
If 2: Abstract (modem)
If 3: Abstract (modem)
If 4: Abstract (modem)
If 5: Ethernet Networking
If 6: Ethernet Networking
Without this change, the 2 network interfaces will be named to usb0 and usb1, our QA think the names are confusing and filed a bug on it.
After applying this change, the name will be wwan0 and wwan1, and they could work well with modem manager.
--- drivers/net/usb/cdc_ether.c | 6 ++++++ 1 file changed, 6 insertions(+)
drivers/net/usb/cdc_ether.c +6 -0
@@ -1000,6 +1000,12 @@ static const struct usb_device_id products[] = { USB_CDC_SUBCLASS_ETHERNET, USB_CDC_PROTO_NONE), .driver_info = (unsigned long)&wwan_info, +}, { +/* Cinterion PLS62-W modem by GEMALTO/THALES */ +USB_DEVICE_AND_INTERFACE_INFO (0x1e2d ,0x005b ,USB_CLASS_COMM , +USB_CDC_SUBCLASS_ETHERNET , + USB_CDC_PROTO_NONE), + .driver_info = (unsigned long )&wwan_info, }, {/* Cinterion PLS83/PLS63 modem by GEMALTO/THALES */ USB_DEVICE_AND_INTERFACE_INFO(0x1e2d, 0x0069, USB_CLASS_COMM,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 102/204 drm: Add orientation quirk for Lenovo ideapad D330-10IGL
In reply to Greg Kroah-HartmanFrom: Patrick Thompson <[email protected]>
[ Upstream commit 0688773f0710528e1ab302c3d6317e269f2e2e6e ]
Panel is 800x1280 but mounted on a detachable form factor sideways.
--- drivers/gpu/drm/drm_panel_orientation_quirks.c | 6 ++++++ 1 file changed, 6 insertions(+)
drivers/gpu/drm/drm_panel_orientation_quirks.c +6 -0
@@ -272,6 +272,12 @@ static const struct dmi_system_id orientation_data[] = { DMI_EXACT_MATCH(DMI_PRODUCT_VERSION, "Lenovo ideapad D330-10IGM"), }, .driver_data = (void *)&lcd1200x1920_rightside_up, + }, { /* Lenovo Ideapad D330-10IGL (HD) */ + .matches = { +DMI_EXACT_MATCH (DMI_SYS_VENDOR ,"LENOVO" ), + DMI_EXACT_MATCH(DMI_PRODUCT_VERSION, "Lenovo ideapad D330-10IGL"), + }, + .driver_data = (void *)&lcd800x1280_rightside_up, }, { /* Lenovo Yoga Book X90F / X91F / X91L */ .matches = {/* Non exact match to match all versions */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 103/204 s390/debug: add _ASM_S390_ prefix to header guard
In reply to Greg Kroah-HartmanFrom: Niklas Schnelle <[email protected]>
[ Upstream commit 0d4d52361b6c29bf771acd4fa461f06d78fb2fac ]
Using DEBUG_H without a prefix is very generic and inconsistent with other header guards in arch/s390/include/asm. In fact it collides with the same name in the ath9k wireless driver though that depends on !S390 via disabled wireless support. Let's just use a consistent header guard name and prevent possible future trouble.
--- arch/s390/include/asm/debug.h | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
arch/s390/include/asm/debug.h +3 -3
@@ -4,8 +4,8 @@* * Copyright IBM Corp. 1999, 2020 */ -#ifndef DEBUG_H -#define DEBUG_H +#ifndef _ASM_S390_DEBUG_H +#define _ASM_S390_DEBUG_H#include <linux/string.h> #include <linux/spinlock.h>
@@ -487,4 +487,4 @@ void debug_register_static(debug_info_t *id, int pages_per_area, int nr_areas);#endif /* MODULE */ -#endif /* DEBUG_H */ +#endif /* _ASM_S390_DEBUG_H */
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 104/204 s390: expicitly align _edata and _end symbols on page boundary
In reply to Greg Kroah-HartmanFrom: Alexander Gordeev <[email protected]>
[ Upstream commit 45d619bdaf799196d702a9ae464b07066d6db2f9 ]
Symbols _edata and _end in the linker script are the only unaligned expicitly on page boundary. Although _end is aligned implicitly by BSS_SECTION macro that is still inconsistent and could lead to a bug if a tool or function would assume that _edata is as aligned as others.
For example, vmem_map_init() function does not align symbols _etext, _einittext etc. Should these symbols be unaligned as well, the size of ranges to update were short on one page.
Instead of fixing every occurrence of this kind in the code and external tools just force the alignment on these two symbols.
--- arch/s390/kernel/vmlinux.lds.S | 2 ++ 1 file changed, 2 insertions(+)
arch/s390/kernel/vmlinux.lds.S +2 -0
@@ -80,6 +80,7 @@ SECTIONS _end_amode31_refs = .; } + . = ALIGN(PAGE_SIZE); _edata = .; /* End of data section */ /* will be freed after init */
@@ -194,6 +195,7 @@ SECTIONS BSS_SECTION(PAGE_SIZE, 4 * PAGE_SIZE, PAGE_SIZE) + . = ALIGN(PAGE_SIZE); _end = . ; /*
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 105/204 perf/x86/msr: Add Emerald Rapids
In reply to Greg Kroah-HartmanFrom: Kan Liang <[email protected]>
[ Upstream commit 69ced4160969025821f2999ff92163ed26568f1c ]
The same as Sapphire Rapids, the SMI_COUNT MSR is also supported on Emerald Rapids. Add Emerald Rapids model.
--- arch/x86/events/msr.c | 1 + 1 file changed, 1 insertion(+)
arch/x86/events/msr.c +1 -0
@@ -69,6 +69,7 @@ static bool test_intel(int idx, void *data)case INTEL_FAM6_BROADWELL_G :case INTEL_FAM6_BROADWELL_X :case INTEL_FAM6_SAPPHIRERAPIDS_X : +case INTEL_FAM6_EMERALDRAPIDS_X :case INTEL_FAM6_ATOM_SILVERMONT :case INTEL_FAM6_ATOM_SILVERMONT_D :
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 106/204 perf/x86/intel/uncore: Add Emerald Rapids
In reply to Greg Kroah-HartmanFrom: Kan Liang <[email protected]>
[ Upstream commit 5268a2842066c227e6ccd94bac562f1e1000244f ]
Quoted 1 line
From the perspective of the uncore PMU, the new Emerald Rapids is the
same as the Sapphire Rapids. The only difference is the event list, which will be supported in the perf tool later.
--- arch/x86/events/intel/uncore.c | 1 + 1 file changed, 1 insertion(+)
arch/x86/events/intel/uncore.c +1 -0
@@ -1829,6 +1829,7 @@ static const struct x86_cpu_id intel_uncore_match[] __initconst = {X86_MATCH_INTEL_FAM6_MODEL (ALDERLAKE , &adl_uncore_init),X86_MATCH_INTEL_FAM6_MODEL (ALDERLAKE_L , &adl_uncore_init),X86_MATCH_INTEL_FAM6_MODEL (SAPPHIRERAPIDS_X , &spr_uncore_init), +X86_MATCH_INTEL_FAM6_MODEL (EMERALDRAPIDS_X , &spr_uncore_init), X86_MATCH_INTEL_FAM6_MODEL(ATOM_TREMONT_D, &snr_uncore_init), {}, };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 107/204 cpufreq: armada-37xx: stop using 0 as NULL pointer
In reply to Greg Kroah-HartmanFrom: Miles Chen <[email protected]>
[ Upstream commit 08f0adb193c008de640fde34a2e00a666c01d77c ]
Use NULL for NULL pointer to fix the following sparse warning:drivers/cpufreq/armada-37xx-cpufreq.c:448:32: sparse: warning: Using plain integer as NULL pointer
--- drivers/cpufreq/armada-37xx-cpufreq.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/cpufreq/armada-37xx-cpufreq.c +1 -1
@@ -445,7 +445,7 @@ static int __init armada37xx_cpufreq_driver_init(void)return -ENODEV ; } - clk =clk_get (cpu_dev,0 ); + clk =clk_get (cpu_dev,NULL );if (IS_ERR (clk)) {dev_err (cpu_dev,"Cannot get clock for CPU0\n" );return PTR_ERR (clk);
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 108/204 ASoC: fsl_ssi: Rename AC97 streams to avoid collisions with AC97 CODEC
In reply to Greg Kroah-HartmanFrom: Mark Brown <[email protected]>
[ Upstream commit 8c6a42b5b0ed6f96624f56954e93eeae107440a6 ]
The SSI driver calls the AC'97 playback and transmit streams "AC97 Playback" and "AC97 Capture" respectively. This is the same name used by the generic AC'97 CODEC driver in ASoC, creating confusion for the Freescale ASoC card when it attempts to use these widgets in routing. Add a "CPU" in the name like the regular DAIs registered by the driver to disambiguate.
--- sound/soc/fsl/fsl-asoc-card.c | 8 ++++---- sound/soc/fsl/fsl_ssi.c | 4 ++-- 2 files changed, 6 insertions(+), 6 deletions(-)
sound/soc/fsl/fsl-asoc-card.c +4 -4
@@ -120,11 +120,11 @@ static const struct snd_soc_dapm_route audio_map[] = {static const struct snd_soc_dapm_route audio_map_ac97[] = {/* 1st half -- Normal DAPM routes */ - {"Playback" ,NULL ,"AC97 Playback" }, - {"AC97 Capture" ,NULL ,"Capture" }, + {"Playback" ,NULL ,"CPU AC97 Playback" }, + {"CPU AC97 Capture" ,NULL ,"Capture" },/* 2nd half -- ASRC DAPM routes */ - {"AC97 Playback" ,NULL ,"ASRC-Playback" }, - {"ASRC-Capture" ,NULL ,"AC97 Capture" }, + {"CPU AC97 Playback" ,NULL ,"ASRC-Playback" }, + {"ASRC-Capture" ,NULL ,"CPU AC97 Capture" }, };static const struct snd_soc_dapm_route audio_map_tx[] = {
sound/soc/fsl/fsl_ssi.c +2 -2
@@ -1160,14 +1160,14 @@ static struct snd_soc_dai_driver fsl_ssi_ac97_dai = { .symmetric_channels = 1, .probe = fsl_ssi_dai_probe, .playback = { - .stream_name = "AC97 Playback", + .stream_name = "CPU AC97 Playback", .channels_min = 2, .channels_max = 2, .rates = SNDRV_PCM_RATE_8000_48000, .formats = SNDRV_PCM_FMTBIT_S16 | SNDRV_PCM_FMTBIT_S20, }, .capture = { - .stream_name = "AC97 Capture", + .stream_name = "CPU AC97 Capture", .channels_min = 2, .channels_max = 2, .rates = SNDRV_PCM_RATE_48000,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 109/204 ASoC: fsl-asoc-card: Fix naming of AC97 CODEC widgets
In reply to Greg Kroah-HartmanFrom: Mark Brown <[email protected]>
[ Upstream commit 242fc66ae6e1e2b8519daacc7590a73cd0e8a6e4 ]
The fsl-asoc-card AC'97 support currently tries to route to Playback and Capture widgets provided by the AC'97 CODEC. This doesn't work since the generic AC'97 driver registers with an "AC97" at the front of the stream and hence widget names, update to reflect reality. It's not clear to me if or how this ever worked.
--- sound/soc/fsl/fsl-asoc-card.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
sound/soc/fsl/fsl-asoc-card.c +2 -2
@@ -120,8 +120,8 @@ static const struct snd_soc_dapm_route audio_map[] = {static const struct snd_soc_dapm_route audio_map_ac97[] = {/* 1st half -- Normal DAPM routes */ - {"Playback" ,NULL ,"CPU AC97 Playback" }, - {"CPU AC97 Capture" ,NULL ,"Capture" }, + {"AC97 Playback" ,NULL ,"CPU AC97 Playback" }, + {"CPU AC97 Capture" ,NULL ,"AC97 Capture" },/* 2nd half -- ASRC DAPM routes */ {"CPU AC97 Playback" ,NULL ,"ASRC-Playback" }, {"ASRC-Capture" ,NULL ,"CPU AC97 Capture" },
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 110/204 spi: spidev: remove debug messages that access spidev->spi without locking
In reply to Greg Kroah-HartmanFrom: Bartosz Golaszewski <[email protected]>
[ Upstream commit 6b35b173dbc1711f8d272e3f322d2ad697015919 ]
The two debug messages in spidev_open() dereference spidev->spi without taking the lock and without checking if it's not null. This can lead to a crash. Drop the messages as they're not needed - the user-space will get informed about ENOMEM with the syscall return value.
--- drivers/spi/spidev.c | 2 -- 1 file changed, 2 deletions(-)
drivers/spi/spidev.c +0 -2
@@ -592,7 +592,6 @@ static int spidev_open(struct inode *inode, struct file *filp)if (!spidev->tx_buffer) { spidev->tx_buffer =kmalloc (bufsiz,GFP_KERNEL );if (!spidev->tx_buffer) { -dev_dbg (&spidev->spi->dev,"open/ENOMEM\n" ); status = -ENOMEM ; goto err_find_dev; }
@@ -601,7 +600,6 @@ static int spidev_open(struct inode *inode, struct file *filp)if (!spidev->rx_buffer) { spidev->rx_buffer =kmalloc (bufsiz,GFP_KERNEL );if (!spidev->rx_buffer) { -dev_dbg (&spidev->spi->dev,"open/ENOMEM\n" ); status = -ENOMEM ; goto err_alloc_rx_buf; }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 111/204 KVM: s390: interrupt: use READ_ONCE() before cmpxchg()
In reply to Greg Kroah-HartmanFrom: Heiko Carstens <[email protected]>
[ Upstream commit 42400d99e9f0728c17240edb9645637ead40f6b9 ]
Use READ_ONCE() before cmpxchg() to prevent that the compiler generates code that fetches the to be compared old value several times from memory.
--- arch/s390/kvm/interrupt.c | 12 ++++++++---- 1 file changed, 8 insertions(+), 4 deletions(-)
arch/s390/kvm/interrupt.c +8 -4
@@ -81,8 +81,9 @@ static int sca_inject_ext_call(struct kvm_vcpu *vcpu, int src_id)struct esca_block *sca = vcpu->kvm->arch.sca;union esca_sigp_ctrl *sigp_ctrl = &(sca->cpu[vcpu->vcpu_id].sigp_ctrl); -union esca_sigp_ctrl new_val = {0 }, old_val = *sigp_ctrl; +union esca_sigp_ctrl new_val = {0 }, old_val; + old_val =READ_ONCE (*sigp_ctrl); new_val.scn = src_id; new_val.c =1 ; old_val.c =0 ;
@@ -93,8 +94,9 @@ static int sca_inject_ext_call(struct kvm_vcpu *vcpu, int src_id)struct bsca_block *sca = vcpu->kvm->arch.sca;union bsca_sigp_ctrl *sigp_ctrl = &(sca->cpu[vcpu->vcpu_id].sigp_ctrl); -union bsca_sigp_ctrl new_val = {0 }, old_val = *sigp_ctrl; +union bsca_sigp_ctrl new_val = {0 }, old_val; + old_val =READ_ONCE (*sigp_ctrl); new_val.scn = src_id; new_val.c =1 ; old_val.c =0 ;
@@ -124,16 +126,18 @@ static void sca_clear_ext_call(struct kvm_vcpu *vcpu)struct esca_block *sca = vcpu->kvm->arch.sca;union esca_sigp_ctrl *sigp_ctrl = &(sca->cpu[vcpu->vcpu_id].sigp_ctrl); -union esca_sigp_ctrl old = *sigp_ctrl; +union esca_sigp_ctrl old; + old =READ_ONCE (*sigp_ctrl); expect = old.value; rc =cmpxchg (&sigp_ctrl->value, old.value,0 ); }else {struct bsca_block *sca = vcpu->kvm->arch.sca;union bsca_sigp_ctrl *sigp_ctrl = &(sca->cpu[vcpu->vcpu_id].sigp_ctrl); -union bsca_sigp_ctrl old = *sigp_ctrl; +union bsca_sigp_ctrl old; + old =READ_ONCE (*sigp_ctrl); expect = old.value; rc =cmpxchg (&sigp_ctrl->value, old.value,0 ); }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 112/204 scsi: hisi_sas: Set a port invalid only if there are no devices attached when refreshing port id
In reply to Greg Kroah-HartmanFrom: Yihang Li <[email protected]>
[ Upstream commit f58c89700630da6554b24fd3df293a24874c10c1 ]
Currently the driver sets the port invalid if one phy in the port is not enabled, which may cause issues in expander situation. In directly attached situation, if phy up doesn't occur in time when refreshing port id, the port is incorrectly set to invalid which will also cause disk lost.
Therefore set a port invalid only if there are no devices attached to the port.
--- drivers/scsi/hisi_sas/hisi_sas_main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/hisi_sas/hisi_sas_main.c +1 -1
@@ -1414,7 +1414,7 @@ static void hisi_sas_refresh_port_id(struct hisi_hba *hisi_hba) device->linkrate = phy->sas_phy.linkrate; hisi_hba->hw->setup_itct (hisi_hba, sas_dev); - }else + }else if (!port->port_attached) port->id =0xff ; } }
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 113/204 r8152: add vendor/device ID pair for Microsoft Devkit
In reply to Greg Kroah-HartmanFrom: Andre Przywara <[email protected]>
[ Upstream commit be53771c87f4e322a9835d3faa9cd73a4ecdec5b ]
The Microsoft Devkit 2023 is a an ARM64 based machine featuring a Realtek 8153 USB3.0-to-GBit Ethernet adapter. As in their other machines, Microsoft uses a custom USB device ID.
Add the respective ID values to the driver. This makes Ethernet work on the MS Devkit device. The chip has been visually confirmed to be a RTL8153.
--- drivers/net/usb/r8152.c | 1 + 1 file changed, 1 insertion(+)
drivers/net/usb/r8152.c +1 -0
@@ -9809,6 +9809,7 @@ static const struct usb_device_id rtl8152_table[] = {REALTEK_USB_DEVICE (VENDOR_ID_MICROSOFT ,0x07ab ),REALTEK_USB_DEVICE (VENDOR_ID_MICROSOFT ,0x07c6 ),REALTEK_USB_DEVICE (VENDOR_ID_MICROSOFT ,0x0927 ), +REALTEK_USB_DEVICE (VENDOR_ID_MICROSOFT ,0x0c5e ),REALTEK_USB_DEVICE (VENDOR_ID_SAMSUNG ,0xa101 ),REALTEK_USB_DEVICE (VENDOR_ID_LENOVO ,0x304f ), REALTEK_USB_DEVICE(VENDOR_ID_LENOVO, 0x3054),
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 114/204 platform/x86: touchscreen_dmi: Add info for the CSL Panther Tab HD
In reply to Greg Kroah-HartmanFrom: Michael Klein <[email protected]>
[ Upstream commit 36c2b9d6710427f802494ba070621cb415198293 ]
Add touchscreen info for the CSL Panther Tab HD.
--- drivers/platform/x86/touchscreen_dmi.c | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+)
drivers/platform/x86/touchscreen_dmi.c +25 -0
@@ -255,6 +255,23 @@ static const struct ts_dmi_data connect_tablet9_data = { .properties = connect_tablet9_props, }; +static const struct property_entry csl_panther_tab_hd_props[] = { +PROPERTY_ENTRY_U32 ("touchscreen-min-x" ,1 ), +PROPERTY_ENTRY_U32 ("touchscreen-min-y" ,20 ), +PROPERTY_ENTRY_U32 ("touchscreen-size-x" ,1980 ), +PROPERTY_ENTRY_U32 ("touchscreen-size-y" ,1526 ), +PROPERTY_ENTRY_BOOL ("touchscreen-inverted-y" ), +PROPERTY_ENTRY_BOOL ("touchscreen-swapped-x-y" ), +PROPERTY_ENTRY_STRING ("firmware-name" ,"gsl1680-csl-panther-tab-hd.fw" ), +PROPERTY_ENTRY_U32 ("silead,max-fingers" ,10 ), + { } +}; + +static const struct ts_dmi_data csl_panther_tab_hd_data = { + .acpi_name ="MSSL1680:00" , + .properties = csl_panther_tab_hd_props, +}; +static const struct property_entry cube_iwork8_air_props[] = {PROPERTY_ENTRY_U32 ("touchscreen-min-x" ,1 ),PROPERTY_ENTRY_U32 ("touchscreen-min-y" ,3 ),
@@ -1100,6 +1117,14 @@ const struct dmi_system_id touchscreen_dmi_table[] = { DMI_MATCH(DMI_PRODUCT_NAME, "Tablet 9"), }, }, + { +/* CSL Panther Tab HD */ + .driver_data = (void *)&csl_panther_tab_hd_data, + .matches = { +DMI_MATCH (DMI_SYS_VENDOR ,"CSL Computer GmbH & Co. KG" ), + DMI_MATCH(DMI_PRODUCT_NAME, "CSL Panther Tab HD"), + }, + }, {/* CUBE iwork8 Air */ .driver_data = (void *)&cube_iwork8_air_data,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 115/204 platform/x86: asus-nb-wmi: Add alternate mapping for KEY_SCREENLOCK
In reply to Greg Kroah-HartmanFrom: Hans de Goede <[email protected]>
[ Upstream commit db9494895b405bf318dc7e563dee6daa51b3b6ed ]
The 0x33 keycode is emitted by Fn + F6 on a ASUS FX705GE laptop.
--- drivers/platform/x86/asus-nb-wmi.c | 1 + 1 file changed, 1 insertion(+)
drivers/platform/x86/asus-nb-wmi.c +1 -0
@@ -521,6 +521,7 @@ static const struct key_entry asus_nb_wmi_keymap[] = { { KE_KEY, 0x30, { KEY_VOLUMEUP } }, { KE_KEY, 0x31, { KEY_VOLUMEDOWN } }, { KE_KEY, 0x32, { KEY_MUTE } }, + { KE_KEY, 0x33, { KEY_SCREENLOCK } }, { KE_KEY, 0x35, { KEY_SCREENLOCK } }, { KE_KEY, 0x40, { KEY_PREVIOUSSONG } }, { KE_KEY, 0x41, { KEY_NEXTSONG } },
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 116/204 lockref: stop doing cpu_relax in the cmpxchg loop
In reply to Greg Kroah-HartmanFrom: Mateusz Guzik <[email protected]>
[ Upstream commit f5fe24ef17b5fbe6db49534163e77499fb10ae8c ]
On the x86-64 architecture even a failing cmpxchg grants exclusive access to the cacheline, making it preferable to retry the failed op immediately instead of stalling with the pause instruction.
To illustrate the impact, below are benchmark results obtained by running various will-it-scale tests on top of the 6.2-rc3 kernel and Cascade Lake (2 sockets * 24 cores * 2 threads) CPU.
All results in ops/s. Note there is some variance in re-runs, but the code is consistently faster when contention is present.
open3 ("Same file open/close"):
proc stock no-pause
1 805603 814942 (+%1)
2 1054980 1054781 (-0%)
8 1544802 1822858 (+18%)
24 1191064 2199665 (+84%)
48 851582 1469860 (+72%)
96 609481 1427170 (+134%) fstat2 ("Same file fstat"):
proc stock no-pause
1 3013872 3047636 (+1%)
2 4284687 4400421 (+2%)
8 3257721 5530156 (+69%)
24 2239819 5466127 (+144%)
48 1701072 5256609 (+209%)
96 1269157 6649326 (+423%)Additionally, a kernel with a private patch to help access() scalability:
access2 ("Same file access"):
proc stock patched patched
+nopause
24 2378041 2005501 5370335 (-15% / +125%)That is, fixing the problems in access itself *reduces* scalability after the cacheline ping-pong only happens in lockref with the pause instruction.
Note that fstat and access benchmarks are not currently integrated into will-it-scale, but interested parties can find them in pull requests to said project.
Code at hand has a rather tortured history. First modification showed up in commit d472d9d98b46 ("lockref: Relax in cmpxchg loop"), written with Itanium in mind. Later it got patched up to use an arch-dependent macro to stop doing it on s390 where it caused a significant regression. Said macro had undergone revisions and was ultimately eliminated later, going back to cpu_relax.
While I intended to only remove cpu_relax for x86-64, I got the following comment from Linus:
I would actually prefer just removing it entirely and see if somebody else hollers. You have the numbers to prove it hurts on real hardware, and I don't think we have any numbers to the contrary.
So I think it's better to trust the numbers and remove it as a failure, than say "let's just remove it on x86-64 and leave everybody else with the potentially broken code"
Additionally, Will Deacon (maintainer of the arm64 port, one of the architectures previously benchmarked):
So, from the arm64 side of the fence, I'm perfectly happy just removing the cpu_relax() calls from lockref.
As such, come back full circle in history and whack it altogether.
--- lib/lockref.c | 1 - 1 file changed, 1 deletion(-)
lib/lockref.c +0 -1
@@ -24,7 +24,6 @@ } \if (!--retry) \break ; \ -cpu_relax (); \ } \ }while (0 )
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 117/204 firmware: coreboot: Check size of table entry and use flex-array
In reply to Greg Kroah-HartmanFrom: Kees Cook <[email protected]>
[ Upstream commit 3b293487b8752cc42c1cbf8a0447bc6076c075fa ]
The memcpy() of the data following a coreboot_table_entry couldn't be evaluated by the compiler under CONFIG_FORTIFY_SOURCE. To make it easier to reason about, add an explicit flexible array member to struct coreboot_device so the entire entry can be copied at once. Additionally, validate the sizes before copying. Avoids this run-time false positive warning:
memcpy: detected field-spanning write (size 168) of single field "&device->entry" at drivers/firmware/google/coreboot_table.c:103 (size 8)
--- drivers/firmware/google/coreboot_table.c | 9 +++++++-- drivers/firmware/google/coreboot_table.h | 1 + 2 files changed, 8 insertions(+), 2 deletions(-)
drivers/firmware/google/coreboot_table.c +7 -2
@@ -93,7 +93,12 @@ static int coreboot_table_populate(struct device *dev, void *ptr)for (i =0 ; i < header->table_entries; i++) { entry = ptr_entry; - device =kzalloc (sizeof (struct device ) + entry->size,GFP_KERNEL ); +if (entry->size <sizeof (*entry)) { +dev_warn (dev,"coreboot table entry too small!\n" ); +return -EINVAL ; + } + + device =kzalloc (sizeof (device->dev) + entry->size,GFP_KERNEL );if (!device)return -ENOMEM ;
@@ -101,7 +106,7 @@ static int coreboot_table_populate(struct device *dev, void *ptr) device->dev.parent = dev; device->dev.bus = &coreboot_bus_type; device->dev.release = coreboot_device_release; -memcpy (&device->entry, ptr_entry, entry->size); +memcpy (device->raw, ptr_entry, entry->size); ret =device_register (&device->dev);if (ret) {
drivers/firmware/google/coreboot_table.h +1 -0
@@ -66,6 +66,7 @@ struct coreboot_device {struct coreboot_table_entry entry;struct lb_cbmem_ref cbmem_ref;struct lb_framebuffer framebuffer; +DECLARE_FLEX_ARRAY (u8, raw); }; };
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 118/204 drm/i915: Allow switching away via vga-switcheroo if uninitialized
In reply to Greg Kroah-HartmanFrom: Thomas Zimmermann <[email protected]>
[ Upstream commit a273e95721e96885971a05f1b34cb6d093904d9d ]
Always allow switching away via vga-switcheroo if the display is uninitalized. Instead prevent switching to i915 if the device has not been initialized.
This issue was introduced by commit 5df7bd130818 ("drm/i915: skip display initialization when there is no display") protected, which protects code paths from being executed on uninitialized devices. In the case of vga-switcheroo, we want to allow a switch away from i915's device. So run vga_switcheroo_process_delayed_switch() and test in the switcheroo callbacks if the i915 device is available.
--- drivers/gpu/drm/i915/i915_drv.c | 3 +-- drivers/gpu/drm/i915/i915_switcheroo.c | 6 +++++- 2 files changed, 6 insertions(+), 3 deletions(-)
drivers/gpu/drm/i915/i915_drv.c +1 -2
@@ -990,8 +990,7 @@ static void i915_driver_lastclose(struct drm_device *dev)intel_fbdev_restore_mode (dev); -if (HAS_DISPLAY (i915)) -vga_switcheroo_process_delayed_switch (); +vga_switcheroo_process_delayed_switch (); }static void i915_driver_postclose (struct drm_device *dev,struct drm_file *file)
drivers/gpu/drm/i915/i915_switcheroo.c +5 -1
@@ -18,6 +18,10 @@ static void i915_switcheroo_set_state(struct pci_dev *pdev,dev_err (&pdev->dev,"DRM not initialized, aborting switch.\n" );return ; } +if (!HAS_DISPLAY (i915)) { +dev_err (&pdev->dev,"Device state not initialized, aborting switch.\n" ); +return ; + }if (state ==VGA_SWITCHEROO_ON ) {drm_info (&i915->drm,"switched on\n" );
@@ -43,7 +47,7 @@ static bool i915_switcheroo_can_switch(struct pci_dev *pdev)* locking inversion with the driver load path. And the access here is * completely racy anyway. So don't bother with locking for now. */ -return i915 &&atomic_read (&i915->drm.open_count) ==0 ; +return i915 &&HAS_DISPLAY (i915) &&atomic_read (&i915->drm.open_count) ==0 ; }static const struct vga_switcheroo_client_ops i915_switcheroo_ops = {
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 119/204 Revert "selftests/bpf: check null propagation only neither reg is PTR_TO_BTF_ID"
In reply to Greg Kroah-HartmanThis reverts commit 95fc28a8e92169cff4b649ae9f4a209a783f2c91.
--- tools/testing/selftests/bpf/prog_tests/jeq_infer_not_null.c | 9 -- tools/testing/selftests/bpf/progs/jeq_infer_not_null_fail.c | 42 ------------ 2 files changed, 51 deletions(-) delete mode 100644 tools/testing/selftests/bpf/prog_tests/jeq_infer_not_null.c delete mode 100644 tools/testing/selftests/bpf/progs/jeq_infer_not_null_fail.c
tools/testing/selftests/bpf/prog_tests/jeq_infer_not_null.c deleted +0 -9
@@ -1,9 +0,0 @@ -// SPDX-License-Identifier: GPL-2.0 - -#include <test_progs.h> -#include "jeq_infer_not_null_fail.skel.h" - -void test_jeq_infer_not_null (void ) -{ -RUN_TESTS (jeq_infer_not_null_fail); -}
tools/testing/selftests/bpf/progs/jeq_infer_not_null_fail.c deleted +0 -42
42 lines not on this page · raw message
Greg Kroah-Hartman
maintainerPATCH 120/204 drm/i915: Remove unused variable
In reply to Greg Kroah-HartmanFrom: Nirmoy Das <[email protected]>
commit 2293a73ad4f3b6c37c06713ff1b67659d92ef43d upstream.
Removed unused i915 var.
--- drivers/gpu/drm/i915/i915_drv.c | 2 -- 1 file changed, 2 deletions(-)
drivers/gpu/drm/i915/i915_drv.c +0 -2
@@ -986,8 +986,6 @@ static int i915_driver_open(struct drm_d*/ static void i915_driver_lastclose (struct drm_device *dev) { -struct drm_i915_private *i915 =to_i915 (dev); -intel_fbdev_restore_mode (dev);vga_switcheroo_process_delayed_switch ();
Greg Kroah-Hartman
maintainerPATCH 121/204 x86: ACPI: cstate: Optimize C3 entry on AMD CPUs
In reply to Greg Kroah-HartmanFrom: Deepak Sharma <[email protected]>
commit a8fb40966f19ff81520d9ccf8f7e2b95201368b8 upstream.
All Zen or newer CPU which support C3 shares cache. Its not necessary to flush the caches in software before entering C3. This will cause drop in performance for the cores which share some caches. ARB_DIS is not used with current AMD C state implementation. So set related flags correctly.
--- arch/x86/kernel/acpi/cstate.c | 15 +++++++++++++++ 1 file changed, 15 insertions(+)
arch/x86/kernel/acpi/cstate.c +15 -0
@@ -79,6 +79,21 @@ void acpi_processor_power_init_bm_check(*/ flags->bm_control =0 ; } +if (c->x86_vendor ==X86_VENDOR_AMD && c->x86 >=0x17 ) { +/* +* For all AMD Zen or newer CPUs that support C3, caches +* should not be flushed by software while entering C3 +* type state. Set bm->check to 1 so that kernel doesn't +* need to execute cache flush operation. +*/ + flags->bm_check =1 ; +/* +* In current AMD C state implementation ARB_DIS is no longer +* used. So set bm_control to zero to indicate ARB_DIS is not +* required while entering C3 type state. +*/ + flags->bm_control =0 ; + } }EXPORT_SYMBOL (acpi_processor_power_init_bm_check);
Greg Kroah-Hartman
maintainerPATCH 122/204 fs: reiserfs: remove useless new_opts in reiserfs_remount
In reply to Greg Kroah-HartmanFrom: Dongliang Mu <[email protected]>
commit 81dedaf10c20959bdf5624f9783f408df26ba7a4 upstream.
Since the commit c3d98ea08291 ("VFS: Don't use save/replace_mount_options if not using generic_show_options") eliminates replace_mount_options in reiserfs_remount, but does not handle the allocated new_opts, it will cause memory leak in the reiserfs_remount.
Because new_opts is useless in reiserfs_mount, so we fix this bug by removing the useless new_opts in reiserfs_remount.
--- fs/reiserfs/super.c | 6 ------ 1 file changed, 6 deletions(-)
fs/reiserfs/super.c +0 -6
@@ -1437,7 +1437,6 @@ static int reiserfs_remount(struct superunsigned long safe_mask =0 ;unsigned int commit_max_age = (unsigned int )-1 ;struct reiserfs_journal *journal =SB_JOURNAL (s); -char *new_opts;int err;char *qf_names[REISERFS_MAXQUOTAS ];unsigned int qfmt =0 ;
@@ -1445,10 +1444,6 @@ static int reiserfs_remount(struct superint i;#endif - new_opts =kstrdup (arg,GFP_KERNEL ); -if (arg && !new_opts) -return -ENOMEM ; -sync_filesystem (s);reiserfs_write_lock (s);
@@ -1599,7 +1594,6 @@ out_ok_unlocked: out_err_unlock:reiserfs_write_unlock (s); out_err: -kfree (new_opts);return err; }
Greg Kroah-Hartman
maintainerPATCH 123/204 sysctl: add a new register_sysctl_init() interface
In reply to Greg Kroah-HartmanFrom: Xiaoming Ni <[email protected]>
commit 3ddd9a808cee7284931312f2f3e854c9617f44b2 upstream.
Patch series "sysctl: first set of kernel/sysctl cleanups", v2.
Finally had time to respin the series of the work we had started last year on cleaning up the kernel/sysct.c kitchen sink. People keeps stuffing their sysctls in that file and this creates a maintenance burden. So this effort is aimed at placing sysctls where they actually belong.
I'm going to split patches up into series as there is quite a bit of work.
This first set adds register_sysctl_init() for uses of registerting a sysctl on the init path, adds const where missing to a few places, generalizes common values so to be more easy to share, and starts the move of a few kernel/sysctl.c out where they belong.
The majority of rework on v2 in this first patch set is 0-day fixes. Eric Biederman's feedback is later addressed in subsequent patch sets.
I'll only post the first two patch sets for now. We can address the rest once the first two patch sets get completely reviewed / Acked.
This patch (of 9):
The kernel/sysctl.c is a kitchen sink where everyone leaves their dirty dishes, this makes it very difficult to maintain.
To help with this maintenance let's start by moving sysctls to places where they actually belong. The proc sysctl maintainers do not want to know what sysctl knobs you wish to add for your own piece of code, we just care about the core logic.
Today though folks heavily rely on tables on kernel/sysctl.c so they can easily just extend this table with their needed sysctls. In order to help users move their sysctls out we need to provide a helper which can be used during code initialization.
We special-case the initialization use of register_sysctl() since it *is* safe to fail, given all that sysctls do is provide a dynamic interface to query or modify at runtime an existing variable. So the use case of register_sysctl() on init should *not* stop if the sysctls don't end up getting registered. It would be counter productive to stop boot if a simple sysctl registration failed.
Provide a helper for init then, and document the recommended init levels to use for callers of this routine. We will later use this in subsequent patches to start slimming down kernel/sysctl.c tables and moving sysctl registration to the code which actually needs these sysctls.
[[email protected]: major commit log and documentation rephrasing also moved to fs/proc/proc_sysctl.c ]
--- fs/proc/proc_sysctl.c | 33 +++++++++++++++++++++++++++++++++ include/linux/sysctl.h | 3 +++ 2 files changed, 36 insertions(+)
fs/proc/proc_sysctl.c +33 -0
@@ -16,6 +16,7 @@#include <linux/module.h> #include <linux/bpf-cgroup.h> #include <linux/mount.h> +#include <linux/kmemleak.h> #include "internal.h" static const struct dentry_operations proc_sys_dentry_operations;
@@ -1384,6 +1385,38 @@ struct ctl_table_header *register_sysctl(const char *path, struct ctl_table *tab }EXPORT_SYMBOL (register_sysctl); +/** +* __register_sysctl_init() - register sysctl table to path +* @path: path name for sysctl base +* @table: This is the sysctl table that needs to be registered to the path +* @table_name: The name of sysctl table, only used for log printing when +* registration fails +* +* The sysctl interface is used by userspace to query or modify at runtime +* a predefined value set on a variable. These variables however have default +* values pre-set. Code which depends on these variables will always work even +* if register_sysctl() fails. If register_sysctl() fails you'd just loose the +* ability to query or modify the sysctls dynamically at run time. Chances of +* register_sysctl() failing on init are extremely low, and so for both reasons +* this function does not return any error as it is used by initialization code. +* +* Context: Can only be called after your respective sysctl base path has been +* registered. So for instance, most base directories are registered early on +* init before init levels are processed through proc_sys_init() and +* sysctl_init(). +*/ +void __init __register_sysctl_init (const char *path,struct ctl_table *table, +const char *table_name) +{ +struct ctl_table_header *hdr =register_sysctl (path, table); + +if (unlikely (!hdr)) { +pr_err ("failed when register_sysctl %s to %s\n" , table_name, path); +return ; + } +kmemleak_not_leak (hdr); +} +static char *append_path (const char *path,char *pos,const char *name) {int namelen;
include/linux/sysctl.h +3 -0
@@ -206,6 +206,9 @@ struct ctl_table_header *register_sysctl_paths(const struct ctl_path *path,void unregister_sysctl_table (struct ctl_table_header * table);extern int sysctl_init (void ); +extern void __register_sysctl_init (const char *path,struct ctl_table *table, +const char *table_name); +#define register_sysctl_init (path, table) __register_sysctl_init(path, table, #table)void do_sysctl_args (void );extern int pwrsw_enabled;
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 124/204 kernel/panic: move panic sysctls to its own file
In reply to Greg Kroah-HartmanFrom: tangmeng <[email protected]>
commit 9df918698408fd914493aba0b7858fef50eba63a upstream.
kernel/sysctl.c is a kitchen sink where everyone leaves their dirty dishes, this makes it very difficult to maintain.
To help with this maintenance let's start by moving sysctls to places where they actually belong. The proc sysctl maintainers do not want to know what sysctl knobs you wish to add for your own piece of code, we just care about the core logic.
All filesystem syctls now get reviewed by fs folks. This commit follows the commit of fs, move the oops_all_cpu_backtrace sysctl to its own file, kernel/panic.c.
--- include/linux/panic.h | 6 ------ kernel/panic.c | 26 +++++++++++++++++++++++++- kernel/sysctl.c | 11 ----------- 3 files changed, 25 insertions(+), 18 deletions(-)
include/linux/panic.h +0 -6
@@ -15,12 +15,6 @@ extern void oops_enter(void);extern void oops_exit (void );extern bool oops_may_print (void ); -#ifdef CONFIG_SMP -extern unsigned int sysctl_oops_all_cpu_backtrace; -#else -#define sysctl_oops_all_cpu_backtrace 0 -#endif /* CONFIG_SMP */ -extern int panic_timeout;extern unsigned long panic_print;extern int panic_on_oops;
kernel/panic.c +25 -1
@@ -42,7 +42,9 @@* Should we dump all CPUs backtraces in an oops event? * Defaults to 0, can be changed via sysctl. */ -unsigned int __read_mostly sysctl_oops_all_cpu_backtrace; +static unsigned int __read_mostly sysctl_oops_all_cpu_backtrace; +#else +#define sysctl_oops_all_cpu_backtrace 0#endif /* CONFIG_SMP */ int panic_on_oops =CONFIG_PANIC_ON_OOPS_VALUE ;
@@ -71,6 +73,28 @@ ATOMIC_NOTIFIER_HEAD(panic_notifier_list);EXPORT_SYMBOL (panic_notifier_list); +#if defined(CONFIG_SMP ) && defined(CONFIG_SYSCTL ) +static struct ctl_table kern_panic_table[] = { + { + .procname ="oops_all_cpu_backtrace" , + .data = &sysctl_oops_all_cpu_backtrace, + .maxlen =sizeof (int ), + .mode =0644 , + .proc_handler = proc_dointvec_minmax, + .extra1 =SYSCTL_ZERO , + .extra2 =SYSCTL_ONE , + }, + { } +}; + +static __init int kernel_panic_sysctls_init (void ) +{ +register_sysctl_init ("kernel" , kern_panic_table); +return 0 ; +} +late_initcall (kernel_panic_sysctls_init); +#endif +static long no_blink (int state) {return 0 ;
kernel/sysctl.c +0 -11
@@ -2220,17 +2220,6 @@ static struct ctl_table kern_table[] = { .proc_handler = proc_dointvec, },#endif -#ifdef CONFIG_SMP - { - .procname = "oops_all_cpu_backtrace", - .data = &sysctl_oops_all_cpu_backtrace, - .maxlen = sizeof(int), - .mode = 0644, - .proc_handler = proc_dointvec_minmax, - .extra1 = SYSCTL_ZERO, - .extra2 = SYSCTL_ONE, - }, -#endif /* CONFIG_SMP */ { .procname = "pid_max", .data = &pid_max,
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 125/204 panic: unset panic_on_warn inside panic()
In reply to Greg Kroah-HartmanFrom: Tiezhu Yang <[email protected]>
commit 1a2383e8b84c0451fd9b1eec3b9aab16f30b597c upstream.
In the current code, the following three places need to unset panic_on_warn before calling panic() to avoid recursive panics:
kernel/kcsan/report.c: print_report()kernel/sched/core.c: __schedule_bug()mm/kfence/report.c: kfence_report_error()
In order to avoid copy-pasting "panic_on_warn = 0" all over the places, it is better to move it inside panic() and then remove it from the other places.
--- kernel/panic.c | 20 +++++++++++--------- 1 file changed, 11 insertions(+), 9 deletions(-)
kernel/panic.c +11 -9
@@ -208,6 +208,16 @@ void panic(const char *fmt, ...)int old_cpu, this_cpu;bool _crash_kexec_post_notifiers = crash_kexec_post_notifiers; +if (panic_on_warn) { +/* +* This thread may hit another WARN() in the panic path. +* Resetting this prevents additional WARN() from panicking the +* system on this thread. Other threads are blocked by the +* panic_mutex in panic(). +*/ + panic_on_warn =0 ; + } +/* * Disable local interrupts. This will prevent panic_smp_self_stop * from deadlocking the first cpu that invokes the panic, since
@@ -616,16 +626,8 @@ void __warn(const char *file, int line, void *caller, unsigned taint,if (regs)show_regs (regs); -if (panic_on_warn) { -/* -* This thread may hit another WARN() in the panic path. -* Resetting this prevents additional WARN() from panicking the -* system on this thread. Other threads are blocked by the -* panic_mutex in panic(). -*/ - panic_on_warn =0 ; +if (panic_on_warn)panic ("panic_on_warn set ...\n" ); - }if (!regs)dump_stack ();
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 126/204 ubsan: no need to unset panic_on_warn in ubsan_epilogue()
In reply to Greg Kroah-HartmanFrom: Tiezhu Yang <[email protected]>
commit d83ce027a54068fabb70d2c252e1ce2da86784a4 upstream.
panic_on_warn is unset inside panic(), so no need to unset it before calling panic() in ubsan_epilogue().
--- lib/ubsan.c | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-)
lib/ubsan.c +1 -9
@@ -154,16 +154,8 @@ static void ubsan_epilogue(void) current->in_ubsan--; -if (panic_on_warn) { -/* -* This thread may hit another WARN() in the panic path. -* Resetting this prevents additional WARN() from panicking the -* system on this thread. Other threads are blocked by the -* panic_mutex in panic(). -*/ - panic_on_warn =0 ; +if (panic_on_warn)panic ("panic_on_warn set ...\n" ); - } }void __ubsan_handle_divrem_overflow (void *_data,void *lhs,void *rhs)
Signature · 1 line
2.39.0
Greg Kroah-Hartman
maintainerPATCH 127/204 kasan: no need to unset panic_on_warn in end_report()
In reply to Greg Kroah-HartmanFrom: Tiezhu Yang <[email protected]>
commit e7ce7500375a63348e1d3a703c8d5003cbe3fea6 upstream.
panic_on_warn is unset inside panic(), so no need to unset it before calling panic() in end_report().
--- mm/kasan/report.c | 10 +--------- 1 file changed, 1 insertion(+), 9 deletions(-)
mm/kasan/report.c +1 -9
@@ -117,16 +117,8 @@ static void end_report(unsigned long *flags, unsigned long addr)pr_err ("==================================================================\n" );add_taint (TAINT_BAD_PAGE ,LOCKDEP_NOW_UNRELIABLE );spin_unlock_irqrestore (&report_lock, *flags); -if (panic_on_warn && !test_bit (KASAN_BIT_MULTI_SHOT , &kasan_flags)) { -/* -* This thread may hit another WARN() in the panic path. -* Resetting this prevents additional WARN() from panicking the -* system on this thread. Other threads are blocked by the -* panic_mutex in panic(). -*/ - panic_on_warn =0 ; +if (panic_on_warn && !test_bit (KASAN_BIT_MULTI_SHOT , &kasan_flags))panic ("panic_on_warn set ...\n" ); - }if (kasan_arg_fault ==KASAN_ARG_FAULT_PANIC )panic ("kasan.fault=panic set ...\n" );kasan_enable_current ();
Signature · 1 line
2.39.0