5.10.215-rc1 review
Subsystems (4)
Greg Kroah-Hartman
maintainerPATCH 131/294 mei: me: add arrow lake point H DID
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alexander Usyskin <[email protected]>
commit 8436f25802ec028ac7254990893f3e01926d9b79 upstream.
Add Arrow Lake H device id.
--- drivers/misc/mei/hw-me-regs.h | 1 + drivers/misc/mei/pci-me.c | 1 + 2 files changed, 2 insertions(+)
drivers/misc/mei/hw-me-regs.h +1 -0
@@ -113,6 +113,7 @@#define MEI_DEV_ID_MTL_M 0x7E70/* Meteor Lake Point M */ #define MEI_DEV_ID_ARL_S 0x7F68/* Arrow Lake Point S */ +#define MEI_DEV_ID_ARL_H 0x7770/* Arrow Lake Point H */ /* * MEI HW Section
drivers/misc/mei/pci-me.c +1 -0
@@ -119,6 +119,7 @@ static const struct pci_device_id mei_me {MEI_PCI_DEVICE(MEI_DEV_ID_MTL_M, MEI_ME_PCH15_CFG)}, {MEI_PCI_DEVICE(MEI_DEV_ID_ARL_S, MEI_ME_PCH15_CFG)}, + {MEI_PCI_DEVICE(MEI_DEV_ID_ARL_H, MEI_ME_PCH15_CFG)},/* required last entry */ {0, }
Greg Kroah-Hartman
maintainerPATCH 132/294 vt: fix unicode buffer corruption when deleting characters
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nicolas Pitre <[email protected]>
commit 1581dafaf0d34bc9c428a794a22110d7046d186d upstream.
This is the same issue that was fixed for the VGA text buffer in commit 39cdb68c64d8 ("vt: fix memory overlapping when deleting chars in the buffer"). The cure is also the same i.e. replace memcpy() with memmove() due to the overlaping buffers.
--- drivers/tty/vt/vt.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/tty/vt/vt.c +1 -1
@@ -398,7 +398,7 @@ static void vc_uniscr_delete(struct vc_dchar32_t *ln = uniscr->lines[vc->state.y];unsigned int x = vc->state.x, cols = vc->vc_cols; -memcpy (&ln[x], &ln[x + nr], (cols - x - nr) *sizeof (*ln)); +memmove (&ln[x], &ln[x + nr], (cols - x - nr) *sizeof (*ln));memset32 (&ln[cols - nr],' ' , nr); } }
Greg Kroah-Hartman
maintainerPATCH 133/294 fs/aio: Check IOCB_AIO_RW before the struct aio_kiocb conversion
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bart Van Assche <[email protected]>
commit 961ebd120565cb60cebe21cb634fbc456022db4a upstream.
The first kiocb_set_cancel_fn() argument may point at a struct kiocb that is not embedded inside struct aio_kiocb. With the current code, depending on the compiler, the req->ki_ctx read happens either before the IOCB_AIO_RW test or after that test. Move the req->ki_ctx read such that it is guaranteed that the IOCB_AIO_RW test happens first.
--- fs/aio.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-)
fs/aio.c +6 -2
@@ -565,8 +565,8 @@ static int aio_setup_ring(struct kioctxvoid kiocb_set_cancel_fn (struct kiocb *iocb,kiocb_cancel_fn *cancel) { - struct aio_kiocb *req = container_of(iocb, struct aio_kiocb, rw); -struct kioctx *ctx = req->ki_ctx; +struct aio_kiocb *req; +struct kioctx *ctx;unsigned long flags;/*
@@ -576,9 +576,13 @@ void kiocb_set_cancel_fn(struct kiocb *iif (!(iocb->ki_flags &IOCB_AIO_RW ))return ; + req = container_of(iocb, struct aio_kiocb, rw); +if (WARN_ON_ONCE (!list_empty (&req->ki_list)))return ; + ctx = req->ki_ctx; +spin_lock_irqsave (&ctx->ctx_lock, flags);list_add_tail (&req->ki_list, &ctx->active_reqs); req->ki_cancel = cancel;
Greg Kroah-Hartman
maintainerPATCH 134/294 tee: optee: Fix kernel panic caused by incorrect error handling
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sumit Garg <[email protected]>
commit 95915ba4b987cf2b222b0f251280228a1ff977ac upstream.
The error path while failing to register devices on the TEE bus has a bug leading to kernel panic as follows:
[ 15.398930] Unable to handle kernel paging request at virtual address ffff07ed00626d7c [ 15.406913] Mem abort info: [ 15.409722] ESR = 0x0000000096000005 [ 15.413490] EC = 0x25: DABT (current EL), IL = 32 bits [ 15.418814] SET = 0, FnV = 0 [ 15.421878] EA = 0, S1PTW = 0 [ 15.425031] FSC = 0x05: level 1 translation fault [ 15.429922] Data abort info: [ 15.432813] ISV = 0, ISS = 0x00000005, ISS2 = 0x00000000 [ 15.438310] CM = 0, WnR = 0, TnD = 0, TagAccess = 0 [ 15.443372] GCS = 0, Overlay = 0, DirtyBit = 0, Xs = 0 [ 15.448697] swapper pgtable: 4k pages, 48-bit VAs, pgdp=00000000d9e3e000 [ 15.455413] [ffff07ed00626d7c] pgd=1800000bffdf9003, p4d=1800000bffdf9003, pud=0000000000000000 [ 15.464146] Internal error: Oops: 0000000096000005 [#1] PREEMPT SMP
Commit 7269cba53d90 ("tee: optee: Fix supplicant based device enumeration") lead to the introduction of this bug. So fix it appropriately.
--- drivers/tee/optee/device.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/tee/optee/device.c +2 -1
@@ -90,13 +90,14 @@ static int optee_register_device(const uif (rc) {pr_err ("device registration failed, err: %d\n" , rc);put_device (&optee_device->dev); +return rc; }if (func ==PTA_CMD_GET_DEVICES_SUPP )device_create_file (&optee_device->dev, &dev_attr_need_supplicant); -return rc; +return 0 ; }static int __optee_enumerate_devices (u32 func)
Greg Kroah-Hartman
maintainerPATCH 135/294 xen/events: close evtchn after mapping cleanup
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Maximilian Heyne <[email protected]>
commit fa765c4b4aed2d64266b694520ecb025c862c5a9 upstream.
shutdown_pirq and startup_pirq are not taking the irq_mapping_update_lock because they can't due to lock inversion. Both are called with the irq_desc->lock being taking. The lock order, however, is first irq_mapping_update_lock and then irq_desc->lock.
This opens multiple races:
- shutdown_pirq can be interrupted by a function that allocates an event channel:
CPU0 CPU1
shutdown_pirq {
xen_evtchn_close(e)
__startup_pirq {
EVTCHNOP_bind_pirq
-> returns just freed evtchn e
set_evtchn_to_irq(e, irq)
}
xen_irq_info_cleanup() {
set_evtchn_to_irq(e, -1)
}
} Assume here event channel e refers here to the same event channel number.
After this race the evtchn_to_irq mapping for e is invalid (-1).
- __startup_pirq races with __unbind_from_irq in a similar way. Because __startup_pirq doesn't take irq_mapping_update_lock it can grab the evtchn that __unbind_from_irq is currently freeing and cleaning up. In this case even though the event channel is allocated, its mapping can be unset in evtchn_to_irq.
The fix is to first cleanup the mappings and then close the event channel. In this way, when an event channel gets allocated it's potential previous evtchn_to_irq mappings are guaranteed to be unset already. This is also the reverse order of the allocation where first the event channel is allocated and then the mappings are setup.
On a 5.10 kernel prior to commit 3fcdaf3d7634 ("xen/events: modify internal [un]bind interfaces"), we hit a BUG like the following during probing of NVMe devices. The issue is that during nvme_setup_io_queues, pci_free_irq is called for every device which results in a call to shutdown_pirq. With many nvme devices it's therefore likely to hit this race during boot because there will be multiple calls to shutdown_pirq and startup_pirq are running potentially in parallel.
------------[ cut here ]------------ blkfront: xvda: barrier or flush: disabled; persistent grants: enabled; indirect descriptors: enabled; bounce buffer: enabled kernel BUG at drivers/xen/events/events_base.c:499! invalid opcode: 0000 [#1] SMP PTI CPU: 44 PID: 375 Comm: kworker/u257:23 Not tainted 5.10.201-191.748.amzn2.x86_64 #1 Hardware name: Xen HVM domU, BIOS 4.11.amazon 08/24/2006 Workqueue: nvme-reset-wq nvme_reset_work RIP: 0010:bind_evtchn_to_cpu+0xdf/0xf0 Code: 5d 41 5e c3 cc cc cc cc 44 89 f7 e8 2b 55 ad ff 49 89 c5 48 85 c0 0f 84 64 ff ff ff 4c 8b 68 30 41 83 fe ff 0f 85 60 ff ff ff <0f> 0b 66 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 40 00 0f 1f 44 00 00 RSP: 0000:ffffc9000d533b08 EFLAGS: 00010046 RAX: 0000000000000000 RBX: 0000000000000000 RCX: 0000000000000006 RDX: 0000000000000028 RSI: 00000000ffffffff RDI: 00000000ffffffff RBP: ffff888107419680 R08: 0000000000000000 R09: ffffffff82d72b00 R10: 0000000000000000 R11: 0000000000000000 R12: 00000000000001ed R13: 0000000000000000 R14: 00000000ffffffff R15: 0000000000000002 FS: 0000000000000000(0000) GS:ffff88bc8b500000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000000000000 CR3: 0000000002610001 CR4: 00000000001706e0 DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 Call Trace: ? show_trace_log_lvl+0x1c1/0x2d9 ? show_trace_log_lvl+0x1c1/0x2d9 ? set_affinity_irq+0xdc/0x1c0 ? __die_body.cold+0x8/0xd ? die+0x2b/0x50 ? do_trap+0x90/0x110 ? bind_evtchn_to_cpu+0xdf/0xf0 ? do_error_trap+0x65/0x80 ? bind_evtchn_to_cpu+0xdf/0xf0 ? exc_invalid_op+0x4e/0x70 ? bind_evtchn_to_cpu+0xdf/0xf0 ? asm_exc_invalid_op+0x12/0x20 ? bind_evtchn_to_cpu+0xdf/0xf0 ? bind_evtchn_to_cpu+0xc5/0xf0 set_affinity_irq+0xdc/0x1c0 irq_do_set_affinity+0x1d7/0x1f0 irq_setup_affinity+0xd6/0x1a0 irq_startup+0x8a/0xf0 __setup_irq+0x639/0x6d0 ? nvme_suspend+0x150/0x150 request_threaded_irq+0x10c/0x180 ? nvme_suspend+0x150/0x150 pci_request_irq+0xa8/0xf0 ? __blk_mq_free_request+0x74/0xa0 queue_request_irq+0x6f/0x80 nvme_create_queue+0x1af/0x200 nvme_create_io_queues+0xbd/0xf0 nvme_setup_io_queues+0x246/0x320 ? nvme_irq_check+0x30/0x30 nvme_reset_work+0x1c8/0x400 process_one_work+0x1b0/0x350 worker_thread+0x49/0x310 ? process_one_work+0x350/0x350 kthread+0x11b/0x140 ? __kthread_bind_mask+0x60/0x60 ret_from_fork+0x22/0x30 Modules linked in: ---[ end trace a11715de1eee1873 ]---
--- drivers/xen/events/events_base.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-)
drivers/xen/events/events_base.c +2 -3
@@ -885,8 +885,8 @@ static void shutdown_pirq(struct irq_datreturn ;do_mask (info,EVT_MASK_REASON_EXPLICIT ); -xen_evtchn_close (evtchn);xen_irq_info_cleanup (info); +xen_evtchn_close (evtchn); }static void enable_pirq (struct irq_data *data)
@@ -929,8 +929,6 @@ static void __unbind_from_irq(unsigned iif (VALID_EVTCHN (evtchn)) {unsigned int cpu =cpu_from_irq (irq); -xen_evtchn_close (evtchn); -switch (type_from_irq (irq)) {case IRQT_VIRQ :per_cpu (virq_to_irq, cpu)[virq_from_irq (irq)] =-1 ;
@@ -943,6 +941,7 @@ static void __unbind_from_irq(unsigned i }xen_irq_info_cleanup (info); +xen_evtchn_close (evtchn); }xen_free_irq (irq);
Greg Kroah-Hartman
maintainerPATCH 136/294 printk: Update @console_may_schedule in console_trylock_spinning()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: John Ogness <[email protected]>
[ Upstream commit 8076972468584d4a21dab9aa50e388b3ea9ad8c7 ]
console_trylock_spinning() may takeover the console lock from a schedulable context. Update @console_may_schedule to make sure it reflects a trylock acquire.
--- kernel/printk/printk.c | 6 ++++++ 1 file changed, 6 insertions(+)
kernel/printk/printk.c +6 -0
@@ -1866,6 +1866,12 @@ static int console_trylock_spinning(void)*/ mutex_acquire (&console_lock_dep_map,0 ,1 , _THIS_IP_); +/* +* Update @console_may_schedule for trylock because the previous +* owner may have been schedulable. +*/ + console_may_schedule =0 ; +return 1 ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 137/294 btrfs: allocate btrfs_ioctl_defrag_range_args on stack
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Goldwyn Rodrigues <[email protected]>
commit c853a5783ebe123847886d432354931874367292 upstream.
Instead of using kmalloc() to allocate btrfs_ioctl_defrag_range_args, allocate btrfs_ioctl_defrag_range_args on stack, the size is reasonably small and ioctls are called in process context.
sizeof(btrfs_ioctl_defrag_range_args) = 48
[ This patch is needed to fix a memory leak of "range" that was introduced when commit 173431b274a9 ("btrfs: defrag: reject unknown flags of btrfs_ioctl_defrag_range_args") was backported to kernels lacking this patch. Now with these two patches applied in reverse order, range->flags needed to change back to range.flags.
This bug was discovered and resolved using Coverity Static Analysis Security Testing (SAST) by Synopsys, Inc.]
--- fs/btrfs/ioctl.c | 25 ++++++++----------------- 1 file changed, 8 insertions(+), 17 deletions(-)
fs/btrfs/ioctl.c +8 -17
@@ -3148,7 +3148,7 @@ static int btrfs_ioctl_defrag(struct fil {struct inode *inode =file_inode (file);struct btrfs_root *root =BTRFS_I (inode)->root; -struct btrfs_ioctl_defrag_range_args *range; +struct btrfs_ioctl_defrag_range_args range = {0 };int ret; ret =mnt_want_write_file (file);
@@ -3180,37 +3180,28 @@ static int btrfs_ioctl_defrag(struct fil goto out; } - range =kzalloc (sizeof (*range),GFP_KERNEL ); -if (!range) { - ret = -ENOMEM ; - goto out; - } -if (argp) { -if (copy_from_user (range, argp, -sizeof (*range))) { +if (copy_from_user (&range, argp,sizeof (range))) { ret = -EFAULT ; -kfree (range); goto out; } -if (range->flags & ~BTRFS_DEFRAG_RANGE_FLAGS_SUPP ) { +if (range.flags & ~BTRFS_DEFRAG_RANGE_FLAGS_SUPP ) { ret = -EOPNOTSUPP ; goto out; }/* compression requires us to start the IO */ -if ((range->flags &BTRFS_DEFRAG_RANGE_COMPRESS )) { - range->flags |=BTRFS_DEFRAG_RANGE_START_IO ; - range->extent_thresh = (u32)-1 ; +if ((range.flags &BTRFS_DEFRAG_RANGE_COMPRESS )) { + range.flags |=BTRFS_DEFRAG_RANGE_START_IO ; + range.extent_thresh = (u32)-1 ; } }else {/* the rest are all set to zero by kzalloc */ - range->len = (u64)-1 ; + range.len = (u64)-1 ; } ret =btrfs_defrag_file (file_inode (file), file, - range,BTRFS_OLDEST_GENERATION ,0 ); + &range,BTRFS_OLDEST_GENERATION ,0 );if (ret >0 ) ret =0 ; -kfree (range);break ;default : ret = -EINVAL ;
Greg Kroah-Hartman
maintainerPATCH 138/294 x86/asm: Add _ASM_RIP() macro for x86-64 (%rip) suffix
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
From: "H. Peter Anvin (Intel)" <[email protected]>
commit f87bc8dc7a7c438c70f97b4e51c76a183313272e upstream.
Add a macro _ASM_RIP() to add a (%rip) suffix on 64 bits only. This is useful for immediate memory references where one doesn't want gcc to possibly use a register indirection as it may in the case of an "m" constraint.
--- arch/x86/include/asm/asm.h | 5 +++++ 1 file changed, 5 insertions(+)
arch/x86/include/asm/asm.h +5 -0
@@ -6,12 +6,14 @@# define __ASM_FORM (x) x# define __ASM_FORM_RAW (x) x# define __ASM_FORM_COMMA (x) x, +# define __ASM_REGPFX %#else #include <linux/stringify.h> # define __ASM_FORM (x) " " __stringify(x) " "# define __ASM_FORM_RAW (x) __stringify(x)# define __ASM_FORM_COMMA (x) " " __stringify(x) "," +# define __ASM_REGPFX %%#endif #ifndef __x86_64__
@@ -48,6 +50,9 @@#define _ASM_SI __ASM_REG(si)#define _ASM_DI __ASM_REG(di) +/* Adds a (%rip) suffix on 64 bits only; for immediate memory references */ +#define _ASM_RIP (x) __ASM_SEL_RAW(x, x (__ASM_REGPFX rip)) +#ifndef __x86_64__/* 32 bit */
Greg Kroah-Hartman
maintainerPATCH 139/294 x86/bugs: Add asm helpers for executing VERW
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit baf8361e54550a48a7087b603313ad013cc13386 upstream.
MDS mitigation requires clearing the CPU buffers before returning to user. This needs to be done late in the exit-to-user path. Current location of VERW leaves a possibility of kernel data ending up in CPU buffers for memory accesses done after VERW such as:
1. Kernel data accessed by an NMI between VERW and return-to-user can remain in CPU buffers since NMI returning to kernel does not execute VERW to clear CPU buffers.
2. Alyssa reported that after VERW is executed, CONFIG_GCC_PLUGIN_STACKLEAK=y scrubs the stack used by a system call. Memory accesses during stack scrubbing can move kernel stack contents into CPU buffers.
3. When caller saved registers are restored after a return from function executing VERW, the kernel stack accesses can remain in CPU buffers(since they occur after VERW).
To fix this VERW needs to be moved very late in exit-to-user path.
In preparation for moving VERW to entry/exit asm code, create macros that can be used in asm. Also make VERW patching depend on a new feature flag X86_FEATURE_CLEAR_CPU_BUF.
[pawan: - Runtime patch jmp instead of verw in macro CLEAR_CPU_BUFFERS
due to lack of relative addressing support for relocations in kernels < v6.5. - Add UNWIND_HINT_EMPTY to avoid warning: arch/x86/entry/entry.o: warning: objtool: mds_verw_sel+0x0: unreachable instruction]
--- arch/x86/entry/entry.S | 23 +++++++++++++++++++++++ arch/x86/include/asm/cpufeatures.h | 1 + arch/x86/include/asm/nospec-branch.h | 15 +++++++++++++++ 3 files changed, 39 insertions(+)
arch/x86/entry/entry.S +23 -0
@@ -6,6 +6,9 @@ #include <linux/linkage.h> #include <asm/export.h> #include <asm/msr-index.h> +#include <asm/unwind_hints.h> +#include <asm/segment.h> +#include <asm/cache.h> .pushsection .noinstr.text, "ax"
@@ -20,3 +23,23 @@ SYM_FUNC_END(entry_ibpb) EXPORT_SYMBOL_GPL(entry_ibpb); .popsection + +/* + * Define the VERW operand that is disguised as entry code so that + * it can be referenced with KPTI enabled. This ensure VERW can be + * used late in exit-to-user path after page tables are switched. + */ +.pushsection .entry.text, "ax" + +.align L1_CACHE_BYTES, 0xcc +SYM_CODE_START_NOALIGN(mds_verw_sel) + UNWIND_HINT_EMPTY + ANNOTATE_NOENDBR + .word __KERNEL_DS +.align L1_CACHE_BYTES, 0xcc +SYM_CODE_END(mds_verw_sel); +/* For KVM */ +EXPORT_SYMBOL_GPL(mds_verw_sel); + +.popsection +
arch/x86/include/asm/cpufeatures.h +1 -0
@@ -300,6 +300,7 @@#define X86_FEATURE_USE_IBPB_FW (11*32+16)/* "" Use IBPB during runtime firmware calls */ #define X86_FEATURE_RSB_VMEXIT_LITE (11*32+17)/* "" Fill RSB on VM exit when EIBRS is enabled */ #define X86_FEATURE_MSR_TSX_CTRL (11*32+18)/* "" MSR IA32_TSX_CTRL (Intel) implemented */ +#define X86_FEATURE_CLEAR_CPU_BUF (11*32+19)/* "" Clear CPU buffers using VERW */ #define X86_FEATURE_SRSO (11*32+24)/* "" AMD BTB untrain RETs */ #define X86_FEATURE_SRSO_ALIAS (11*32+25)/* "" AMD BTB untrain RETs through aliasing */
arch/x86/include/asm/nospec-branch.h +15 -0
@@ -182,6 +182,19 @@#endif .endm +/* + * Macro to execute VERW instruction that mitigate transient data sampling + * attacks such as MDS. On affected systems a microcode update overloaded VERW + * instruction to also clear the CPU buffers. VERW clobbers CFLAGS.ZF. + * + * Note: Only the memory operand variant of VERW clears the CPU buffers. + */ +.macro CLEAR_CPU_BUFFERS + ALTERNATIVE "jmp .Lskip_verw_\@", "", X86_FEATURE_CLEAR_CPU_BUF + verw _ASM_RIP(mds_verw_sel) +.Lskip_verw_\@: +.endm + #else /* __ASSEMBLY__ */#define ANNOTATE_RETPOLINE_SAFE \
@@ -362,6 +375,8 @@ DECLARE_STATIC_KEY_FALSE(mds_idle_clear)DECLARE_STATIC_KEY_FALSE (mmio_stale_data_clear); +extern u16 mds_verw_sel; +#include <asm/segment.h> /**
Greg Kroah-Hartman
maintainerPATCH 140/294 x86/entry_64: Add VERW just before userspace transition
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit 3c7501722e6b31a6e56edd23cea5e77dbb9ffd1a upstream.
Mitigation for MDS is to use VERW instruction to clear any secrets in CPU Buffers. Any memory accesses after VERW execution can still remain in CPU buffers. It is safer to execute VERW late in return to user path to minimize the window in which kernel data can end up in CPU buffers. There are not many kernel secrets to be had after SWITCH_TO_USER_CR3.
Add support for deploying VERW mitigation after user register state is restored. This helps minimize the chances of kernel data ending up into CPU buffers after executing VERW.
Note that the mitigation at the new location is not yet enabled.
Corner case not handled
=======================
Interrupts returning to kernel don't clear CPUs buffers since the exit-to-user path is expected to do that anyways. But, there could be a case when an NMI is generated in kernel after the exit-to-user path has cleared the buffers. This case is not handled and NMI returning to kernel don't clear CPU buffers because:
1. It is rare to get an NMI after VERW, but before returning to user.
2. For an unprivileged user, there is no known way to make that NMI less rare or target it.
3. It would take a large number of these precisely-timed NMIs to mount an actual attack. There's presumably not enough bandwidth.
4. The NMI in question occurs after a VERW, i.e. when user state is restored and most interesting data is already scrubbed. Whats left is only the data that NMI touches, and that may or may not be of any interest.
[ pawan: resolved conflict in syscall_return_via_sysret, added
CLEAR_CPU_BUFFERS to USERGS_SYSRET64 ]
--- arch/x86/entry/entry_64.S | 10 ++++++++++ arch/x86/entry/entry_64_compat.S | 1 + arch/x86/include/asm/irqflags.h | 1 + 3 files changed, 12 insertions(+)
arch/x86/entry/entry_64.S +10 -0
@@ -615,6 +615,7 @@ SYM_INNER_LABEL(swapgs_restore_regs_and_ /* Restore RDI. */ popq %rdi SWAPGS + CLEAR_CPU_BUFFERS INTERRUPT_RETURN
@@ -721,6 +722,8 @@ native_irq_return_ldt: */ popq %rax /* Restore user RAX */ + CLEAR_CPU_BUFFERS + /* * RSP now points to an ordinary IRET frame, except that the page * is read-only and RSP[31:16] are preloaded with the userspace
@@ -1488,6 +1491,12 @@ nmi_restore: movq $0, 5*8(%rsp) /* clear "NMI executing" */ /* + * Skip CLEAR_CPU_BUFFERS here, since it only helps in rare cases like + * NMI in kernel after user state is restored. For an unprivileged user + * these conditions are hard to meet. + */ + + /* * iretq reads the "iret" frame and exits the NMI stack in a * single instruction. We are returning to kernel mode, so this * cannot result in a fault. Similarly, we don't need to worry
@@ -1504,6 +1513,7 @@ SYM_CODE_END(asm_exc_nmi) SYM_CODE_START(ignore_sysret) UNWIND_HINT_EMPTY mov $-ENOSYS, %eax + CLEAR_CPU_BUFFERS sysretl SYM_CODE_END(ignore_sysret) #endif
arch/x86/entry/entry_64_compat.S +1 -0
@@ -319,6 +319,7 @@ sysret32_from_system_call: xorl %r9d, %r9d xorl %r10d, %r10d swapgs + CLEAR_CPU_BUFFERS sysretl SYM_CODE_END(entry_SYSCALL_compat)
arch/x86/include/asm/irqflags.h +1 -0
@@ -134,6 +134,7 @@ static __always_inline unsigned long arc#define INTERRUPT_RETURN jmp native_iret#define USERGS_SYSRET64 \ swapgs; \ + CLEAR_CPU_BUFFERS; \ sysretq;#define USERGS_SYSRET32 \ swapgs; \
Greg Kroah-Hartman
maintainerPATCH 141/294 x86/entry_32: Add VERW just before userspace transition
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit a0e2dab44d22b913b4c228c8b52b2a104434b0b3 upstream.
As done for entry_64, add support for executing VERW late in exit to user path for 32-bit mode.
--- arch/x86/entry/entry_32.S | 3 +++ 1 file changed, 3 insertions(+)
arch/x86/entry/entry_32.S +3 -0
@@ -949,6 +949,7 @@ SYM_FUNC_START(entry_SYSENTER_32) BUG_IF_WRONG_CR3 no_user_check=1 popfl popl %eax + CLEAR_CPU_BUFFERS /* * Return back to the vDSO, which will pop ecx and edx.
@@ -1021,6 +1022,7 @@ restore_all_switch_stack: /* Restore user state */ RESTORE_REGS pop=4 # skip orig_eax/error_code + CLEAR_CPU_BUFFERS .Lirq_return: /* * ARCH_HAS_MEMBARRIER_SYNC_CORE rely on IRET core serialization
@@ -1219,6 +1221,7 @@ SYM_CODE_START(asm_exc_nmi) /* Not on SYSENTER stack. */ call exc_nmi + CLEAR_CPU_BUFFERS jmp .Lnmi_return .Lnmi_from_sysenter_stack:
Greg Kroah-Hartman
maintainerPATCH 142/294 x86/bugs: Use ALTERNATIVE() instead of mds_user_clear static key
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit 6613d82e617dd7eb8b0c40b2fe3acea655b1d611 upstream.
The VERW mitigation at exit-to-user is enabled via a static branch mds_user_clear. This static branch is never toggled after boot, and can be safely replaced with an ALTERNATIVE() which is convenient to use in asm.
Switch to ALTERNATIVE() to use the VERW mitigation late in exit-to-user path. Also remove the now redundant VERW in exc_nmi() and arch_exit_to_user_mode().
--- Documentation/x86/mds.rst | 36 +++++++++++++++++++++++++---------- arch/x86/include/asm/entry-common.h | 1 arch/x86/include/asm/nospec-branch.h | 12 ----------- arch/x86/kernel/cpu/bugs.c | 15 +++++--------- arch/x86/kernel/nmi.c | 3 -- arch/x86/kvm/vmx/vmx.c | 2 - 6 files changed, 33 insertions(+), 36 deletions(-)
Documentation/x86/mds.rst +26 -10
@@ -95,6 +95,9 @@ The kernel provides a function to invoke mds_clear_cpu_buffers() +Also macro CLEAR_CPU_BUFFERS can be used in ASM late in exit-to-user path. +Other than CFLAGS.ZF, this macro doesn't clobber any registers. + The mitigation is invoked on kernel/userspace, hypervisor/guest and C-state (idle) transitions.
@@ -138,17 +141,30 @@ Mitigation points When transitioning from kernel to user space the CPU buffers are flushed on affected CPUs when the mitigation is not disabled on the kernel - command line. The migitation is enabled through the static key - mds_user_clear. + command line. The mitigation is enabled through the feature flag + X86_FEATURE_CLEAR_CPU_BUF. - The mitigation is invoked in prepare_exit_to_usermode() which covers - all but one of the kernel to user space transitions. The exception - is when we return from a Non Maskable Interrupt (NMI), which is - handled directly in do_nmi(). - - (The reason that NMI is special is that prepare_exit_to_usermode() can - enable IRQs. In NMI context, NMIs are blocked, and we don't want to - enable IRQs with NMIs blocked.) + The mitigation is invoked just before transitioning to userspace after + user registers are restored. This is done to minimize the window in + which kernel data could be accessed after VERW e.g. via an NMI after + VERW. + + **Corner case not handled** + Interrupts returning to kernel don't clear CPUs buffers since the + exit-to-user path is expected to do that anyways. But, there could be + a case when an NMI is generated in kernel after the exit-to-user path + has cleared the buffers. This case is not handled and NMI returning to + kernel don't clear CPU buffers because: + + 1. It is rare to get an NMI after VERW, but before returning to userspace. + 2. For an unprivileged user, there is no known way to make that NMI + less rare or target it. + 3. It would take a large number of these precisely-timed NMIs to mount + an actual attack. There's presumably not enough bandwidth. + 4. The NMI in question occurs after a VERW, i.e. when user state is + restored and most interesting data is already scrubbed. Whats left + is only the data that NMI touches, and that may or may not be of + any interest. 2. C-State transition
arch/x86/include/asm/entry-common.h +0 -1
@@ -77,7 +77,6 @@ static inline void arch_exit_to_user_mod static __always_inline void arch_exit_to_user_mode(void) { -mds_user_clear_cpu_buffers ();amd_clear_divider (); }#define arch_exit_to_user_mode arch_exit_to_user_mode
arch/x86/include/asm/nospec-branch.h +0 -12
@@ -370,7 +370,6 @@ DECLARE_STATIC_KEY_FALSE(switch_to_cond_DECLARE_STATIC_KEY_FALSE (switch_mm_cond_ibpb);DECLARE_STATIC_KEY_FALSE (switch_mm_always_ibpb); -DECLARE_STATIC_KEY_FALSE (mds_user_clear);DECLARE_STATIC_KEY_FALSE (mds_idle_clear);DECLARE_STATIC_KEY_FALSE (mmio_stale_data_clear);
@@ -403,17 +402,6 @@ static __always_inline void mds_clear_cp }/** -* mds_user_clear_cpu_buffers - Mitigation for MDS and TAA vulnerability -* -* Clear CPU buffers if the corresponding static key is enabled -*/ -static __always_inline void mds_user_clear_cpu_buffers(void) -{ -if (static_branch_likely (&mds_user_clear)) -mds_clear_cpu_buffers (); -} - -/** * mds_idle_clear_cpu_buffers - Mitigation for MDS vulnerability * * Clear CPU buffers if the corresponding static key is enabled
arch/x86/kernel/cpu/bugs.c +6 -9
@@ -109,9 +109,6 @@ DEFINE_STATIC_KEY_FALSE(switch_mm_cond_i/* Control unconditional IBPB in switch_mm() */ DEFINE_STATIC_KEY_FALSE (switch_mm_always_ibpb); -/* Control MDS CPU buffer clear before returning to user space */ -DEFINE_STATIC_KEY_FALSE (mds_user_clear); -EXPORT_SYMBOL_GPL (mds_user_clear);/* Control MDS CPU buffer clear before idling (halt, mwait) */ DEFINE_STATIC_KEY_FALSE (mds_idle_clear);EXPORT_SYMBOL_GPL (mds_idle_clear);
@@ -249,7 +246,7 @@ static void __init mds_select_mitigationif (!boot_cpu_has (X86_FEATURE_MD_CLEAR )) mds_mitigation =MDS_MITIGATION_VMWERV ; -static_branch_enable (&mds_user_clear); +setup_force_cpu_cap (X86_FEATURE_CLEAR_CPU_BUF );if (!boot_cpu_has (X86_BUG_MSBDS_ONLY ) && (mds_nosmt ||cpu_mitigations_auto_nosmt ()))
@@ -353,7 +350,7 @@ static void __init taa_select_mitigation* For guests that can't determine whether the correct microcode is * present on host, enable the mitigation for UCODE_NEEDED as well. */ -static_branch_enable (&mds_user_clear); +setup_force_cpu_cap (X86_FEATURE_CLEAR_CPU_BUF );if (taa_nosmt ||cpu_mitigations_auto_nosmt ())cpu_smt_disable (false);
@@ -421,7 +418,7 @@ static void __init mmio_select_mitigatio*/ if (boot_cpu_has_bug (X86_BUG_MDS ) || (boot_cpu_has_bug (X86_BUG_TAA ) &&boot_cpu_has (X86_FEATURE_RTM ))) -static_branch_enable (&mds_user_clear); +setup_force_cpu_cap (X86_FEATURE_CLEAR_CPU_BUF );else static_branch_enable (&mmio_stale_data_clear);
@@ -481,12 +478,12 @@ static void __init md_clear_update_mitigif (cpu_mitigations_off ())return ; -if (!static_key_enabled (&mds_user_clear)) +if (!boot_cpu_has (X86_FEATURE_CLEAR_CPU_BUF )) goto out;/* -* mds_user_clear is now enabled. Update MDS, TAA and MMIO Stale Data -* mitigation, if necessary. +* X86_FEATURE_CLEAR_CPU_BUF is now enabled. Update MDS, TAA and MMIO +* Stale Data mitigation, if necessary. */ if (mds_mitigation ==MDS_MITIGATION_OFF &&boot_cpu_has_bug (X86_BUG_MDS )) {
arch/x86/kernel/nmi.c +0 -3
@@ -519,9 +519,6 @@ nmi_restart:write_cr2 (this_cpu_read (nmi_cr2));if (this_cpu_dec_return (nmi_state)) goto nmi_restart; - -if (user_mode (regs)) -mds_user_clear_cpu_buffers (); }#if defined(CONFIG_X86_64 ) &&IS_ENABLED (CONFIG_KVM_INTEL )
arch/x86/kvm/vmx/vmx.c +1 -1
@@ -6795,7 +6795,7 @@ static noinstr void vmx_vcpu_enter_exit(/* L1D Flush includes CPU buffer clear to mitigate MDS */ if (static_branch_unlikely (&vmx_l1d_should_flush))vmx_l1d_flush (vcpu); -else if (static_branch_unlikely (&mds_user_clear)) +else if (cpu_feature_enabled (X86_FEATURE_CLEAR_CPU_BUF ))mds_clear_cpu_buffers ();else if (static_branch_unlikely (&mmio_stale_data_clear) &&kvm_arch_has_assigned_device (vcpu->kvm))
Greg Kroah-Hartman
maintainerPATCH 143/294 KVM/VMX: Use BT+JNC, i.e. EFLAGS.CF to select VMRESUME vs. VMLAUNCH
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
From: Sean Christopherson <[email protected]>
commit 706a189dcf74d3b3f955e9384785e726ed6c7c80 upstream.
Use EFLAGS.CF instead of EFLAGS.ZF to track whether to use VMRESUME versus VMLAUNCH. Freeing up EFLAGS.ZF will allow doing VERW, which clobbers ZF, for MDS mitigations as late as possible without needing to duplicate VERW for both paths.
[ pawan: resolved merge conflict in __vmx_vcpu_run in backport. ]
--- arch/x86/kvm/vmx/run_flags.h | 7 +++++-- arch/x86/kvm/vmx/vmenter.S | 6 +++--- 2 files changed, 8 insertions(+), 5 deletions(-)
arch/x86/kvm/vmx/run_flags.h +5 -2
@@ -2,7 +2,10 @@#ifndef __KVM_X86_VMX_RUN_FLAGS_H#define __KVM_X86_VMX_RUN_FLAGS_H -#define VMX_RUN_VMRESUME (1 << 0) -#define VMX_RUN_SAVE_SPEC_CTRL (1 << 1) +#define VMX_RUN_VMRESUME_SHIFT 0 +#define VMX_RUN_SAVE_SPEC_CTRL_SHIFT 1 + +#define VMX_RUN_VMRESUME BIT(VMX_RUN_VMRESUME_SHIFT) +#define VMX_RUN_SAVE_SPEC_CTRL BIT(VMX_RUN_SAVE_SPEC_CTRL_SHIFT)#endif /* __KVM_X86_VMX_RUN_FLAGS_H */
arch/x86/kvm/vmx/vmenter.S +3 -3
@@ -77,7 +77,7 @@ SYM_FUNC_START(__vmx_vcpu_run) mov (%_ASM_SP), %_ASM_AX /* Check if vmlaunch or vmresume is needed */ - testb $VMX_RUN_VMRESUME, %bl + bt $VMX_RUN_VMRESUME_SHIFT, %bx /* Load guest registers. Don't clobber flags. */ mov VCPU_RCX(%_ASM_AX), %_ASM_CX
@@ -99,8 +99,8 @@ SYM_FUNC_START(__vmx_vcpu_run) /* Load guest RAX. This kills the @regs pointer! */ mov VCPU_RAX(%_ASM_AX), %_ASM_AX - /* Check EFLAGS.ZF from 'testb' above */ - jz .Lvmlaunch + /* Check EFLAGS.CF from the VMX_RUN_VMRESUME bit test above. */ + jnc .Lvmlaunch /* * After a successful VMRESUME/VMLAUNCH, control flow "magically"
Greg Kroah-Hartman
maintainerPATCH 144/294 KVM/VMX: Move VERW closer to VMentry for MDS mitigation
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit 43fb862de8f628c5db5e96831c915b9aebf62d33 upstream.
During VMentry VERW is executed to mitigate MDS. After VERW, any memory access like register push onto stack may put host data in MDS affected CPU buffers. A guest can then use MDS to sample host data.
Although likelihood of secrets surviving in registers at current VERW callsite is less, but it can't be ruled out. Harden the MDS mitigation by moving the VERW mitigation late in VMentry path.
Note that VERW for MMIO Stale Data mitigation is unchanged because of the complexity of per-guest conditional VERW which is not easy to handle that late in asm with no GPRs available. If the CPU is also affected by MDS, VERW is unconditionally executed late in asm regardless of guest having MMIO access.
[ pawan: conflict resolved in backport ]
--- arch/x86/kvm/vmx/vmenter.S | 3 +++ arch/x86/kvm/vmx/vmx.c | 12 ++++++++---- 2 files changed, 11 insertions(+), 4 deletions(-)
arch/x86/kvm/vmx/vmenter.S +3 -0
@@ -99,6 +99,9 @@ SYM_FUNC_START(__vmx_vcpu_run) /* Load guest RAX. This kills the @regs pointer! */ mov VCPU_RAX(%_ASM_AX), %_ASM_AX + /* Clobbers EFLAGS.ZF */ + CLEAR_CPU_BUFFERS + /* Check EFLAGS.CF from the VMX_RUN_VMRESUME bit test above. */ jnc .Lvmlaunch
arch/x86/kvm/vmx/vmx.c +8 -4
@@ -397,7 +397,8 @@ static __always_inline void vmx_enable_fstatic void vmx_update_fb_clear_dis (struct kvm_vcpu *vcpu,struct vcpu_vmx *vmx) { - vmx->disable_fb_clear = vmx_fb_clear_ctrl_available; + vmx->disable_fb_clear = !cpu_feature_enabled (X86_FEATURE_CLEAR_CPU_BUF ) && + vmx_fb_clear_ctrl_available;/* * If guest will not execute VERW, there is no need to set FB_CLEAR_DIS
@@ -6792,11 +6793,14 @@ static noinstr void vmx_vcpu_enter_exit(guest_enter_irqoff ();lockdep_hardirqs_on (CALLER_ADDR0 ); -/* L1D Flush includes CPU buffer clear to mitigate MDS */ +/* +* L1D Flush includes CPU buffer clear to mitigate MDS, but VERW +* mitigation for MDS is done late in VMentry and is still +* executed in spite of L1D Flush. This is because an extra VERW +* should not matter much after the big hammer L1D Flush. +*/ if (static_branch_unlikely (&vmx_l1d_should_flush))vmx_l1d_flush (vcpu); -else if (cpu_feature_enabled (X86_FEATURE_CLEAR_CPU_BUF )) -mds_clear_cpu_buffers ();else if (static_branch_unlikely (&mmio_stale_data_clear) &&kvm_arch_has_assigned_device (vcpu->kvm))mds_clear_cpu_buffers ();
Greg Kroah-Hartman
maintainerPATCH 145/294 x86/mmio: Disable KVM mitigation when X86_FEATURE_CLEAR_CPU_BUF is set
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit e95df4ec0c0c9791941f112db699fae794b9862a upstream.
Currently MMIO Stale Data mitigation for CPUs not affected by MDS/TAA is to only deploy VERW at VMentry by enabling mmio_stale_data_clear static branch. No mitigation is needed for kernel->user transitions. If such CPUs are also affected by RFDS, its mitigation may set X86_FEATURE_CLEAR_CPU_BUF to deploy VERW at kernel->user and VMentry. This could result in duplicate VERW at VMentry.
Fix this by disabling mmio_stale_data_clear static branch when X86_FEATURE_CLEAR_CPU_BUF is enabled.
--- arch/x86/kernel/cpu/bugs.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-)
arch/x86/kernel/cpu/bugs.c +12 -2
@@ -419,6 +419,13 @@ static void __init mmio_select_mitigatioif (boot_cpu_has_bug (X86_BUG_MDS ) || (boot_cpu_has_bug (X86_BUG_TAA ) &&boot_cpu_has (X86_FEATURE_RTM )))setup_force_cpu_cap (X86_FEATURE_CLEAR_CPU_BUF ); + +/* +* X86_FEATURE_CLEAR_CPU_BUF could be enabled by other VERW based +* mitigations, disable KVM-only mitigation in that case. +*/ +if (boot_cpu_has (X86_FEATURE_CLEAR_CPU_BUF )) +static_branch_disable (&mmio_stale_data_clear);else static_branch_enable (&mmio_stale_data_clear);
@@ -495,8 +502,11 @@ static void __init md_clear_update_mitig taa_mitigation =TAA_MITIGATION_VERW ;taa_select_mitigation (); } -if (mmio_mitigation ==MMIO_MITIGATION_OFF && -boot_cpu_has_bug (X86_BUG_MMIO_STALE_DATA )) { +/* +* MMIO_MITIGATION_OFF is not checked here so that mmio_stale_data_clear +* gets updated correctly as per X86_FEATURE_CLEAR_CPU_BUF state. +*/ +if (boot_cpu_has_bug (X86_BUG_MMIO_STALE_DATA )) { mmio_mitigation =MMIO_MITIGATION_VERW ;mmio_select_mitigation (); }
Greg Kroah-Hartman
maintainerPATCH 146/294 Documentation/hw-vuln: Add documentation for RFDS
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit 4e42765d1be01111df0c0275bbaf1db1acef346e upstream.
Add the documentation for transient execution vulnerability Register File Data Sampling (RFDS) that affects Intel Atom CPUs.
[ pawan: s/ATOM_GRACEMONT/ALDERLAKE_N/ ]
--- Documentation/admin-guide/hw-vuln/index.rst | 1 Documentation/admin-guide/hw-vuln/reg-file-data-sampling.rst | 104 +++++++++++ 2 files changed, 105 insertions(+)
Documentation/admin-guide/hw-vuln/index.rst +1 -0
@@ -18,3 +18,4 @@ are configurable at compile, boot or run processor_mmio_stale_data.rst gather_data_sampling.rst srso + reg-file-data-sampling
Documentation/admin-guide/hw-vuln/reg-file-data-sampling.rst new file +104 -0
104 lines not on this page · raw message
Greg Kroah-Hartman
maintainerPATCH 147/294 x86/rfds: Mitigate Register File Data Sampling (RFDS)
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit 8076fcde016c9c0e0660543e67bff86cb48a7c9c upstream.
RFDS is a CPU vulnerability that may allow userspace to infer kernel stale data previously used in floating point registers, vector registers and integer registers. RFDS only affects certain Intel Atom processors.
Intel released a microcode update that uses VERW instruction to clear the affected CPU buffers. Unlike MDS, none of the affected cores support SMT.
Add RFDS bug infrastructure and enable the VERW based mitigation by default, that clears the affected buffers just before exiting to userspace. Also add sysfs reporting and cmdline parameter "reg_file_data_sampling" to control the mitigation.
For details see:Documentation/admin-guide/hw-vuln/reg-file-data-sampling.rst
[ pawan: - Resolved conflicts in sysfs reporting.
- s/ATOM_GRACEMONT/ALDERLAKE_N/ATOM_GRACEMONT is called ALDERLAKE_N in 6.6. ]
--- Documentation/ABI/testing/sysfs-devices-system-cpu | 1 Documentation/admin-guide/kernel-parameters.txt | 21 +++++ arch/x86/Kconfig | 11 ++ arch/x86/include/asm/cpufeatures.h | 1 arch/x86/include/asm/msr-index.h | 8 ++ arch/x86/kernel/cpu/bugs.c | 78 ++++++++++++++++++++- arch/x86/kernel/cpu/common.c | 38 +++++++++- drivers/base/cpu.c | 8 ++ include/linux/cpu.h | 2 9 files changed, 162 insertions(+), 6 deletions(-)
Documentation/ABI/testing/sysfs-devices-system-cpu +1 -0
@@ -507,6 +507,7 @@ What: /sys/devices/system/cpu/vulnerabi /sys/devices/system/cpu/vulnerabilities/mds /sys/devices/system/cpu/vulnerabilities/meltdown /sys/devices/system/cpu/vulnerabilities/mmio_stale_data + /sys/devices/system/cpu/vulnerabilities/reg_file_data_sampling /sys/devices/system/cpu/vulnerabilities/retbleed /sys/devices/system/cpu/vulnerabilities/spec_store_bypass /sys/devices/system/cpu/vulnerabilities/spectre_v1
Documentation/admin-guide/kernel-parameters.txt +21 -0
@@ -993,6 +993,26 @@ The filter can be disabled or changed to another driver later using sysfs. + reg_file_data_sampling= + [X86] Controls mitigation for Register File Data + Sampling (RFDS) vulnerability. RFDS is a CPU + vulnerability which may allow userspace to infer + kernel data values previously stored in floating point + registers, vector registers, or integer registers. + RFDS only affects Intel Atom processors. + + on: Turns ON the mitigation. + off: Turns OFF the mitigation. + + This parameter overrides the compile time default set + by CONFIG_MITIGATION_RFDS. Mitigation cannot be + disabled when other VERW based mitigations (like MDS) + are enabled. In order to disable RFDS mitigation all + VERW based mitigations need to be disabled. + + For details see: + Documentation/admin-guide/hw-vuln/reg-file-data-sampling.rst + driver_async_probe= [KNL] List of driver names to be probed asynchronously. Format: <driver_name1>,<driver_name2>...
@@ -2919,6 +2939,7 @@ nopti [X86,PPC] nospectre_v1 [X86,PPC] nospectre_v2 [X86,PPC,S390,ARM64] + reg_file_data_sampling=off [X86] retbleed=off [X86] spec_store_bypass_disable=off [X86,PPC] spectre_v2_user=off [X86]
arch/x86/Kconfig +11 -0
@@ -2508,6 +2508,17 @@ config GDS_FORCE_MITIGATION If in doubt, say N. +config MITIGATION_RFDS + bool "RFDS Mitigation" + depends on CPU_SUP_INTEL + default y + help + Enable mitigation for Register File Data Sampling (RFDS) by default. + RFDS is a hardware vulnerability which affects Intel Atom CPUs. It + allows unprivileged speculative access to stale data previously + stored in floating point, vector and integer registers. + See also <file:Documentation/admin-guide/hw-vuln/reg-file-data-sampling.rst> + endif config ARCH_HAS_ADD_PAGES
arch/x86/include/asm/cpufeatures.h +1 -0
@@ -454,4 +454,5 @@/* BUG word 2 */ #define X86_BUG_SRSO X86_BUG(1*32 + 0)/* AMD SRSO bug */ #define X86_BUG_DIV0 X86_BUG(1*32 + 1)/* AMD DIV0 speculation bug */ +#define X86_BUG_RFDS X86_BUG(1*32 + 2)/* CPU is vulnerable to Register File Data Sampling */ #endif /* _ASM_X86_CPUFEATURES_H */
arch/x86/include/asm/msr-index.h +8 -0
@@ -168,6 +168,14 @@* CPU is not vulnerable to Gather * Data Sampling (GDS). */ +#define ARCH_CAP_RFDS_NO BIT(27)/* +* Not susceptible to Register +* File Data Sampling. +*/ +#define ARCH_CAP_RFDS_CLEAR BIT(28)/* +* VERW clears CPU Register +* File. +*/ #define MSR_IA32_FLUSH_CMD 0x0000010b#define L1D_FLUSH BIT(0)/*
arch/x86/kernel/cpu/bugs.c +75 -3
120 lines not on this page · raw message
arch/x86/kernel/cpu/common.c +35 -3
@@ -1132,6 +1132,8 @@ static const __initconst struct x86_cpu_#define SRSO BIT(5)/* CPU is affected by GDS */ #define GDS BIT(6) +/* CPU is affected by Register File Data Sampling */ +#define RFDS BIT(7)static const struct x86_cpu_id cpu_vuln_blacklist[]__initconst = {VULNBL_INTEL_STEPPINGS (IVYBRIDGE ,X86_STEPPING_ANY ,SRBDS ),
@@ -1159,9 +1161,18 @@ static const struct x86_cpu_id cpu_vuln_VULNBL_INTEL_STEPPINGS (TIGERLAKE ,X86_STEPPING_ANY ,GDS ),VULNBL_INTEL_STEPPINGS (LAKEFIELD ,X86_STEPPING_ANY ,MMIO |MMIO_SBDS |RETBLEED ),VULNBL_INTEL_STEPPINGS (ROCKETLAKE ,X86_STEPPING_ANY ,MMIO |RETBLEED |GDS ), -VULNBL_INTEL_STEPPINGS (ATOM_TREMONT ,X86_STEPPING_ANY ,MMIO |MMIO_SBDS ), -VULNBL_INTEL_STEPPINGS (ATOM_TREMONT_D ,X86_STEPPING_ANY ,MMIO ), -VULNBL_INTEL_STEPPINGS (ATOM_TREMONT_L ,X86_STEPPING_ANY ,MMIO |MMIO_SBDS ), +VULNBL_INTEL_STEPPINGS (ALDERLAKE ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (ALDERLAKE_L ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (RAPTORLAKE ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (RAPTORLAKE_P ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (RAPTORLAKE_S ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (ALDERLAKE_N ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (ATOM_TREMONT ,X86_STEPPING_ANY ,MMIO |MMIO_SBDS |RFDS ), +VULNBL_INTEL_STEPPINGS (ATOM_TREMONT_D ,X86_STEPPING_ANY ,MMIO |RFDS ), +VULNBL_INTEL_STEPPINGS (ATOM_TREMONT_L ,X86_STEPPING_ANY ,MMIO |MMIO_SBDS |RFDS ), +VULNBL_INTEL_STEPPINGS (ATOM_GOLDMONT ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (ATOM_GOLDMONT_D ,X86_STEPPING_ANY ,RFDS ), +VULNBL_INTEL_STEPPINGS (ATOM_GOLDMONT_PLUS ,X86_STEPPING_ANY ,RFDS ),VULNBL_AMD (0x15 ,RETBLEED ), VULNBL_AMD(0x16, RETBLEED),
@@ -1195,6 +1206,24 @@ static bool arch_cap_mmio_immune(u64 ia3 ia32_cap & ARCH_CAP_SBDR_SSDP_NO); } +static bool __init vulnerable_to_rfds (u64 ia32_cap) +{ +/* The "immunity" bit trumps everything else: */ +if (ia32_cap &ARCH_CAP_RFDS_NO ) +return false; + +/* +* VMMs set ARCH_CAP_RFDS_CLEAR for processors not in the blacklist to +* indicate that mitigation is needed because guest is running on a +* vulnerable hardware or may migrate to such hardware: +*/ +if (ia32_cap &ARCH_CAP_RFDS_CLEAR ) +return true; + +/* Only consult the blacklist when there is no enumeration: */ +return cpu_matches (cpu_vuln_blacklist,RFDS ); +} +static void __init cpu_set_bug_bits (struct cpuinfo_x86 *c) {u64 ia32_cap =x86_read_arch_cap_msr ();
@@ -1303,6 +1332,9 @@ static void __init cpu_set_bug_bits(strusetup_force_cpu_bug (X86_BUG_SRSO ); } +if (vulnerable_to_rfds (ia32_cap)) +setup_force_cpu_bug (X86_BUG_RFDS ); +if (cpu_matches (cpu_vuln_whitelist,NO_MELTDOWN ))return ;
drivers/base/cpu.c +8 -0
@@ -591,6 +591,12 @@ ssize_t __weak cpu_show_spec_rstack_overreturn sysfs_emit (buf,"Not affected\n" ); } +ssize_t __weak cpu_show_reg_file_data_sampling (struct device *dev, +struct device_attribute *attr,char *buf) +{ +return sysfs_emit (buf,"Not affected\n" ); +} + static DEVICE_ATTR(meltdown, 0444, cpu_show_meltdown, NULL); static DEVICE_ATTR(spectre_v1, 0444, cpu_show_spectre_v1, NULL); static DEVICE_ATTR(spectre_v2, 0444, cpu_show_spectre_v2, NULL);
@@ -604,6 +610,7 @@ static DEVICE_ATTR(mmio_stale_data, 0444 static DEVICE_ATTR(retbleed, 0444, cpu_show_retbleed, NULL); static DEVICE_ATTR(gather_data_sampling, 0444, cpu_show_gds, NULL); static DEVICE_ATTR(spec_rstack_overflow, 0444, cpu_show_spec_rstack_overflow, NULL); +static DEVICE_ATTR(reg_file_data_sampling, 0444, cpu_show_reg_file_data_sampling, NULL);static struct attribute *cpu_root_vulnerabilities_attrs[] = { &dev_attr_meltdown.attr,
@@ -619,6 +626,7 @@ static struct attribute *cpu_root_vulner &dev_attr_retbleed.attr, &dev_attr_gather_data_sampling.attr, &dev_attr_spec_rstack_overflow.attr, + &dev_attr_reg_file_data_sampling.attr, NULL };
include/linux/cpu.h +2 -0
@@ -74,6 +74,8 @@ extern ssize_t cpu_show_spec_rstack_over struct device_attribute *attr, char *buf);extern ssize_t cpu_show_gds (struct device *dev,struct device_attribute *attr,char *buf); +extern ssize_t cpu_show_reg_file_data_sampling (struct device *dev, +struct device_attribute *attr,char *buf); extern __printf(4, 5) struct device *cpu_device_create(struct device *parent, void *drvdata,
Greg Kroah-Hartman
maintainerPATCH 148/294 KVM/x86: Export RFDS_NO and RFDS_CLEAR to guests
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pawan Gupta <[email protected]>
commit 2a0180129d726a4b953232175857d442651b55a0 upstream.
Mitigation for RFDS requires RFDS_CLEAR capability which is enumerated by MSR_IA32_ARCH_CAPABILITIES bit 27. If the host has it set, export it to guests so that they can deploy the mitigation.
RFDS_NO indicates that the system is not vulnerable to RFDS, export it to guests so that they don't deploy the mitigation unnecessarily. When the host is not affected by X86_BUG_RFDS, but has RFDS_NO=0, synthesize RFDS_NO to the guest.
--- arch/x86/kvm/x86.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
arch/x86/kvm/x86.c +4 -1
@@ -1389,7 +1389,8 @@ static unsigned int num_msr_based_featur ARCH_CAP_SKIP_VMENTRY_L1DFLUSH | ARCH_CAP_SSB_NO | ARCH_CAP_MDS_NO | \ ARCH_CAP_PSCHANGE_MC_NO | ARCH_CAP_TSX_CTRL_MSR | ARCH_CAP_TAA_NO | \ ARCH_CAP_SBDR_SSDP_NO | ARCH_CAP_FBSDP_NO | ARCH_CAP_PSDP_NO | \ - ARCH_CAP_FB_CLEAR | ARCH_CAP_RRSBA | ARCH_CAP_PBRSB_NO | ARCH_CAP_GDS_NO) + ARCH_CAP_FB_CLEAR | ARCH_CAP_RRSBA | ARCH_CAP_PBRSB_NO | ARCH_CAP_GDS_NO | \ + ARCH_CAP_RFDS_NO | ARCH_CAP_RFDS_CLEAR)static u64 kvm_get_arch_capabilities (void ) {
@@ -1426,6 +1427,8 @@ static u64 kvm_get_arch_capabilities(voi data |=ARCH_CAP_SSB_NO ;if (!boot_cpu_has_bug (X86_BUG_MDS )) data |=ARCH_CAP_MDS_NO ; +if (!boot_cpu_has_bug (X86_BUG_RFDS )) + data |=ARCH_CAP_RFDS_NO ;if (!boot_cpu_has (X86_FEATURE_RTM )) {/*
Greg Kroah-Hartman
maintainerPATCH 149/294 perf/core: Fix reentry problem in perf_output_read_group()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Yang Jihong <[email protected]>
commit 6b959ba22d34ca793ffdb15b5715457c78e38b1a upstream.
perf_output_read_group may respond to IPI request of other cores and invoke __perf_install_in_context function. As a result, hwc configuration is modified. causing inconsistency and unexpected consequences.
Interrupts are not disabled when perf_output_read_group reads PMU counter. In this case, IPI request may be received from other cores.
As a result, PMU configuration is modified and an error occurs when reading PMU counter:
CPU0 CPU1
__se_sys_perf_event_open
perf_install_in_context
perf_output_read_group smp_call_function_single
for_each_sibling_event(sub, leader) { generic_exec_single
if ((sub != event) && remote_function
(sub->state == PERF_EVENT_STATE_ACTIVE)) |
<enter IPI handler: __perf_install_in_context> <----RAISE IPI-----+
__perf_install_in_context
ctx_resched
event_sched_out
armpmu_del
...
hwc->idx = -1; // event->hwc.idx is set to -1
...
<exit IPI>
sub->pmu->read(sub);
armpmu_read
armv8pmu_read_counter
armv8pmu_read_hw_counter
int idx = event->hw.idx; // idx = -1
u64 val = armv8pmu_read_evcntr(idx);
u32 counter = ARMV8_IDX_TO_COUNTER(idx); // invalid counter = 30
read_pmevcntrn(counter) // undefined instruction--- kernel/events/core.c | 9 +++++++++ 1 file changed, 9 insertions(+)
kernel/events/core.c +9 -0
@@ -6890,9 +6890,16 @@ static void perf_output_read_group(struc {struct perf_event *leader = event->group_leader, *sub;u64 read_format = event->attr.read_format; +unsigned long flags;u64 values[6 ];int n =0 ; +/* +* Disabling interrupts avoids all counter scheduling +* (context switches, timer based rotation and IPIs). +*/ +local_irq_save (flags); + values[n++] =1 + leader->nr_siblings;if (read_format &PERF_FORMAT_TOTAL_TIME_ENABLED )
@@ -6928,6 +6935,8 @@ static void perf_output_read_group(struc__output_copy (handle, values, n *sizeof (u64)); } + +local_irq_restore (flags); }#define PERF_FORMAT_TOTAL_TIMES (PERF_FORMAT_TOTAL_TIME_ENABLED|\
Greg Kroah-Hartman
maintainerPATCH 150/294 efivarfs: Request at most 512 bytes for variable names
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tim Schumacher <[email protected]>
commit f45812cc23fb74bef62d4eb8a69fe7218f4b9f2a upstream.
Work around a quirk in a few old (2011-ish) UEFI implementations, where a call to GetNextVariableName with a buffer size larger than 512 bytes will always return EFI_INVALID_PARAMETER.
There is some lore around EFI variable names being up to 1024 bytes in size, but this has no basis in the UEFI specification, and the upper bounds are typically platform specific, and apply to the entire variable (name plus payload).
Given that Linux does not permit creating files with names longer than NAME_MAX (255) bytes, 512 bytes (== 256 UTF-16 characters) is a reasonable limit.
--- drivers/firmware/efi/vars.c | 17 +++++++++++------ 1 file changed, 11 insertions(+), 6 deletions(-)
drivers/firmware/efi/vars.c +11 -6
@@ -415,7 +415,7 @@ int efivar_init(int (*func)(efi_char16_t void *data, bool duplicates, struct list_head *head) { const struct efivar_operations *ops; -unsigned long variable_name_size =1024 ; +unsigned long variable_name_size =512 ;efi_char16_t *variable_name;efi_status_t status;efi_guid_t vendor_guid;
@@ -438,12 +438,13 @@ int efivar_init(int (*func)(efi_char16_t }/* -* Per EFI spec, the maximum storage allocated for both -* the variable name and variable data is 1024 bytes. +* A small set of old UEFI implementations reject sizes +* above a certain threshold, the lowest seen in the wild +* is 512. */ do { - variable_name_size = 1024; + variable_name_size = 512; status = ops->get_next_variable(&variable_name_size, variable_name,
@@ -491,9 +492,13 @@ int efivar_init(int (*func)(efi_char16_tbreak ;case EFI_NOT_FOUND :break ; +case EFI_BUFFER_TOO_SMALL : +pr_warn ("efivars: Variable name size exceeds maximum (%lu > 512)\n" , + variable_name_size); + status =EFI_NOT_FOUND ; +break ;default : -printk (KERN_WARNING "efivars: get_next_variable: status=%lx\n" , - status); +pr_warn ("efivars: get_next_variable: status=%lx\n" , status); status =EFI_NOT_FOUND ;break ; }
Greg Kroah-Hartman
maintainerPATCH 151/294 powerpc: xor_vmx: Add -mhard-float to CFLAGS
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nathan Chancellor <[email protected]>
commit 35f20786c481d5ced9283ff42de5c69b65e5ed13 upstream.
arch/powerpc/lib/xor_vmx.o is built with '-msoft-float' (from the main powerpc Makefile) and '-maltivec' (from its CFLAGS), which causes an error when building with clang after a recent change in main:
error: option '-msoft-float' cannot be specified with '-maltivec' make[6]: *** [scripts/Makefile.build:243: arch/powerpc/lib/xor_vmx.o] Error 1
Explicitly add '-mhard-float' before '-maltivec' in xor_vmx.o's CFLAGS to override the previous inclusion of '-msoft-float' (as the last option wins), which matches how other areas of the kernel use '-maltivec', such as AMDGPU.
--- arch/powerpc/lib/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/powerpc/lib/Makefile +1 -1
@@ -67,6 +67,6 @@ obj-$(CONFIG_PPC_LIB_RHEAP) += rheap.o obj-$(CONFIG_FTR_FIXUP_SELFTEST) += feature-fixups-test.o obj-$(CONFIG_ALTIVEC) += xor_vmx.o xor_vmx_glue.o -CFLAGS_xor_vmx.o += -maltivec $(call cc-option,-mabi=altivec) +CFLAGS_xor_vmx.o += -mhard-float -maltivec $(call cc-option,-mabi=altivec) obj-$(CONFIG_PPC64) += $(obj64-y)
Greg Kroah-Hartman
maintainerPATCH 152/294 serial: sc16is7xx: convert from _raw_ to _noinc_ regmap functions for FIFO
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hugo Villeneuve <[email protected]>
commit dbf4ab821804df071c8b566d9813083125e6d97b upstream.
The SC16IS7XX IC supports a burst mode to access the FIFOs where the initial register address is sent ($00), followed by all the FIFO data without having to resend the register address each time. In this mode, the IC doesn't increment the register address for each R/W byte.
The regmap_raw_read() and regmap_raw_write() are functions which can perform IO over multiple registers. They are currently used to read/write from/to the FIFO, and although they operate correctly in this burst mode on the SPI bus, they would corrupt the regmap cache if it was not disabled manually. The reason is that when the R/W size is more than 1 byte, these functions assume that the register address is incremented and handle the cache accordingly.
Convert FIFO R/W functions to use the regmap _noinc_ versions in order to remove the manual cache control which was a workaround when using the _raw_ versions. FIFO registers are properly declared as volatile so cache will not be used/updated for FIFO accesses.
--- drivers/tty/serial/sc16is7xx.c | 15 +++++++++------ 1 file changed, 9 insertions(+), 6 deletions(-)
drivers/tty/serial/sc16is7xx.c +9 -6
@@ -376,9 +376,7 @@ static void sc16is7xx_fifo_read(struct uconst u8 line =sc16is7xx_line (port);u8 addr = (SC16IS7XX_RHR_REG <<SC16IS7XX_REG_SHIFT ) | line; -regcache_cache_bypass (s->regmap, true); -regmap_raw_read (s->regmap, addr, s->buf, rxlen); -regcache_cache_bypass (s->regmap, false); +regmap_noinc_read (s->regmap, addr, s->buf, rxlen); }static void sc16is7xx_fifo_write (struct uart_port *port,u8 to_send)
@@ -394,9 +392,7 @@ static void sc16is7xx_fifo_write(structif (unlikely (!to_send))return ; -regcache_cache_bypass (s->regmap, true); -regmap_raw_write (s->regmap, addr, s->buf, to_send); -regcache_cache_bypass (s->regmap, false); +regmap_noinc_write (s->regmap, addr, s->buf, to_send); } static void sc16is7xx_port_update(struct uart_port *port, u8 reg,
@@ -489,6 +485,11 @@ static bool sc16is7xx_regmap_precious(streturn false; } +static bool sc16is7xx_regmap_noinc (struct device *dev,unsigned int reg) +{ +return reg ==SC16IS7XX_RHR_REG ; +} +static int sc16is7xx_set_baud (struct uart_port *port,int baud) {struct sc16is7xx_port *s =dev_get_drvdata (port->dev);
@@ -1439,6 +1440,8 @@ static struct regmap_config regcfg = { .cache_type = REGCACHE_RBTREE, .volatile_reg = sc16is7xx_regmap_volatile, .precious_reg = sc16is7xx_regmap_precious, + .writeable_noinc_reg = sc16is7xx_regmap_noinc, + .readable_noinc_reg = sc16is7xx_regmap_noinc, };#ifdef CONFIG_SERIAL_SC16IS7XX_SPI
Greg Kroah-Hartman
maintainerPATCH 153/294 mm/memory-failure: fix an incorrect use of tail pages
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Liu Shixin <[email protected]>
When backport commit c79c5a0a00a9 to 5.10-stable, there is a mistake change. The head page instead of tail page should be passed to try_to_unmap(), otherwise unmap will failed as follows.
Memory failure: 0x121c10: failed to unmap page (mapcount=1) Memory failure: 0x121c10: recovery action for unmapping failed page: Ignored
--- mm/memory-failure.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
mm/memory-failure.c +1 -1
@@ -1075,7 +1075,7 @@ static bool hwpoison_user_mappings(struc unmap_success = false; } }else { - unmap_success =try_to_unmap (p, ttu); + unmap_success =try_to_unmap (hpage, ttu); } }if (!unmap_success)
Greg Kroah-Hartman
maintainerPATCH 154/294 mm/migrate: set swap entry values of THP tail pages properly.
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zi Yan <[email protected]>
The tail pages in a THP can have swap entry information stored in their private field. When migrating to a new page, all tail pages of the new page need to update ->private to avoid future data corruption.
This fix is stable-only, since after commit 07e09c483cbe ("mm/huge_memory:
work on folio->swap instead of page->private when splitting folio"), subpages of a swapcached THP no longer requires the maintenance.
Adding THPs to the swapcache was introduced in commit 38d8b4e6bdc87 ("mm, THP, swap: delay splitting THP during swap out"), where each subpage of a THP added to the swapcache had its own swapcache entry and required the ->private field to point to the correct swapcache entry. Later, when THP migration functionality was implemented in commit 616b8371539a6 ("mm: thp: enable thp migration in generic path"), it initially did not handle the subpages of swapcached THPs, failing to update their ->private fields or replace the subpage pointers in the swapcache. Subsequently, commit e71769ae5260 ("mm: enable thp migration for shmem thp") addressed the swapcache update aspect. This patch fixes the update of subpage ->private fields.
--- mm/migrate.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
mm/migrate.c +5 -1
@@ -447,8 +447,12 @@ int migrate_page_move_mapping(struct addif (PageSwapBacked (page)) {__SetPageSwapBacked (newpage);if (PageSwapCache (page)) { +int i; +SetPageSwapCache (newpage); -set_page_private (newpage,page_private (page)); +for (i =0 ; i < (1 <<compound_order (page)); i++) +set_page_private (newpage + i, +page_private (page + i)); } }else {VM_BUG_ON_PAGE (PageSwapCache (page), page);
Greg Kroah-Hartman
maintainerPATCH 155/294 init: open /initrd.image with O_LARGEFILE
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: John Sperbeck <[email protected]>
commit 4624b346cf67400ef46a31771011fb798dd2f999 upstream.
If initrd data is larger than 2Gb, we'll eventually fail to write to the /initrd.image file when we hit that limit, unless O_LARGEFILE is set.
--- init/initramfs.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
init/initramfs.c +1 -1
@@ -589,7 +589,7 @@ static void __init populate_initrd_imageprintk (KERN_INFO "rootfs image is not initramfs (%s); looks like an initrd\n" , err); - file =filp_open ("/initrd.image" ,O_WRONLY |O_CREAT ,0700 ); + file =filp_open ("/initrd.image" ,O_WRONLY |O_CREAT |O_LARGEFILE ,0700 );if (IS_ERR (file))return ;
Greg Kroah-Hartman
maintainerPATCH 156/294 wifi: mac80211: check/clear fast rx for non-4addr sta VLAN changes
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Felix Fietkau <[email protected]>
commit 4f2bdb3c5e3189297e156b3ff84b140423d64685 upstream.
When moving a station out of a VLAN and deleting the VLAN afterwards, the fast_rx entry still holds a pointer to the VLAN's netdev, which can cause use-after-free bugs. Fix this by immediately calling ieee80211_check_fast_rx after the VLAN change.
--- net/mac80211/cfg.c | 5 ++--- 1 file changed, 2 insertions(+), 3 deletions(-)
net/mac80211/cfg.c +2 -3
@@ -1811,15 +1811,14 @@ static int ieee80211_change_station(stru }if (sta->sdata->vif.type ==NL80211_IFTYPE_AP_VLAN && - sta->sdata->u.vlan.sta) { -ieee80211_clear_fast_rx (sta); + sta->sdata->u.vlan.sta)RCU_INIT_POINTER (sta->sdata->u.vlan.sta,NULL ); - }if (test_sta_flag (sta,WLAN_STA_AUTHORIZED ))ieee80211_vif_dec_num_mcast (sta->sdata); sta->sdata = vlansdata; +ieee80211_check_fast_rx (sta);ieee80211_check_fast_xmit (sta);if (test_sta_flag (sta,WLAN_STA_AUTHORIZED )) {
Greg Kroah-Hartman
maintainerPATCH 157/294 exec: Fix NOMMU linux_binprm::exec in transfer_args_to_stack()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Max Filippov <[email protected]>
commit 2aea94ac14d1e0a8ae9e34febebe208213ba72f7 upstream.
In NOMMU kernel the value of linux_binprm::p is the offset inside the temporary program arguments array maintained in separate pages in the linux_binprm::page. linux_binprm::exec being a copy of linux_binprm::p thus must be adjusted when that array is copied to the user stack. Without that adjustment the value passed by the NOMMU kernel to the ELF program in the AT_EXECFN entry of the aux array doesn't make any sense and it may break programs that try to access memory pointed to by that entry.
Adjust linux_binprm::exec before the successful return from the transfer_args_to_stack().
--- fs/exec.c | 1 + 1 file changed, 1 insertion(+)
fs/exec.c +1 -0
@@ -888,6 +888,7 @@ int transfer_args_to_stack(struct linux_ goto out; } + bprm->exec += *sp_location -MAX_ARG_PAGES *PAGE_SIZE ; *sp_location = sp; out:
Greg Kroah-Hartman
maintainerPATCH 158/294 hexagon: vmlinux.lds.S: handle attributes section
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nathan Chancellor <[email protected]>
commit 549aa9678a0b3981d4821bf244579d9937650562 upstream.
After the linked LLVM change, the build fails with CONFIG_LD_ORPHAN_WARN_LEVEL="error", which happens with allmodconfig:
ld.lld: error: vmlinux.a(init/main.o):(.hexagon.attributes) is being placed in '.hexagon.attributes'
Handle the attributes section in a similar manner as arm and riscv by adding it after the primary ELF_DETAILS grouping in vmlinux.lds.S, which fixes the error.
--- arch/hexagon/kernel/vmlinux.lds.S | 1 + 1 file changed, 1 insertion(+)
arch/hexagon/kernel/vmlinux.lds.S +1 -0
@@ -64,6 +64,7 @@ SECTIONS STABS_DEBUG DWARF_DEBUG ELF_DETAILS + .hexagon.attributes 0 : { *(.hexagon.attributes) } DISCARDS }
Greg Kroah-Hartman
maintainerPATCH 159/294 mmc: core: Initialize mmc_blk_ioc_data
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mikko Rapeli <[email protected]>
commit 0cdfe5b0bf295c0dee97436a8ed13336933a0211 upstream.
Commit 4d0c8d0aef63 ("mmc: core: Use mrq.sbc in close-ended ffu") adds flags uint to struct mmc_blk_ioc_data, but it does not get initialized for RPMB ioctls which now fails.
Let's fix this by always initializing the struct and flags to zero.
--- drivers/mmc/core/block.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/mmc/core/block.c +1 -1
@@ -359,7 +359,7 @@ static struct mmc_blk_ioc_data *mmc_blk_struct mmc_blk_ioc_data *idata;int err; - idata =kmalloc (sizeof (*idata),GFP_KERNEL ); + idata =kzalloc (sizeof (*idata),GFP_KERNEL );if (!idata) { err = -ENOMEM ; goto out;
Greg Kroah-Hartman
maintainerPATCH 160/294 mmc: core: Avoid negative index with array access
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mikko Rapeli <[email protected]>
commit cf55a7acd1ed38afe43bba1c8a0935b51d1dc014 upstream.
Commit 4d0c8d0aef63 ("mmc: core: Use mrq.sbc in close-ended ffu") assigns prev_idata = idatas[i - 1], but doesn't check that the iterator i is greater than zero. Let's fix this by adding a check.
--- drivers/mmc/core/block.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/mmc/core/block.c +1 -1
@@ -468,7 +468,7 @@ static int __mmc_blk_ioctl_cmd(struct mmif (idata->flags &MMC_BLK_IOC_DROP )return 0 ; -if (idata->flags &MMC_BLK_IOC_SBC ) +if (idata->flags &MMC_BLK_IOC_SBC && i >0 ) prev_idata = idatas[i -1 ];/*
Greg Kroah-Hartman
maintainerPATCH 161/294 net: ll_temac: platform_get_resource replaced by wrong function
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Claus Hansen Ries <[email protected]>
commit 3a38a829c8bc27d78552c28e582eb1d885d07d11 upstream.
The function platform_get_resource was replaced with devm_platform_ioremap_resource_byname and is called using 0 as name.
This eventually ends up in platform_get_resource_byname in the call stack, where it causes a null pointer in strcmp.
if (type == resource_type(r) && !strcmp(r->name, name))
It should have been replaced with devm_platform_ioremap_resource.
--- drivers/net/ethernet/xilinx/ll_temac_main.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/net/ethernet/xilinx/ll_temac_main.c +1 -1
@@ -1427,7 +1427,7 @@ static int temac_probe(struct platform_d }/* map device registers */ - lp->regs =devm_platform_ioremap_resource_byname (pdev,0 ); + lp->regs =devm_platform_ioremap_resource (pdev,0 );if (IS_ERR (lp->regs)) {dev_err (&pdev->dev,"could not map TEMAC registers\n" );return -ENOMEM ;
Greg Kroah-Hartman
maintainerPATCH 162/294 usb: cdc-wdm: close race between read and workqueue
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Oliver Neukum <[email protected]>
commit 339f83612f3a569b194680768b22bf113c26a29d upstream.
wdm_read() cannot race with itself. However, in service_outstanding_interrupt() it can race with the workqueue, which can be triggered by error handling.
Hence we need to make sure that the WDM_RESPONDING flag is not just only set but tested.
--- drivers/usb/class/cdc-wdm.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/usb/class/cdc-wdm.c +5 -1
@@ -471,6 +471,7 @@ out_free_mem:static int service_outstanding_interrupt (struct wdm_device *desc) {int rv =0 ; +int used;/* submit read urb only if the device is waiting for it */ if (!desc->resp_count || !--desc->resp_count)
@@ -485,7 +486,10 @@ static int service_outstanding_interrupt goto out; } -set_bit (WDM_RESPONDING , &desc->flags); + used =test_and_set_bit (WDM_RESPONDING , &desc->flags); +if (used) + goto out; +spin_unlock_irq (&desc->iuspin); rv =usb_submit_urb (desc->response,GFP_KERNEL );spin_lock_irq (&desc->iuspin);
Greg Kroah-Hartman
maintainerPATCH 163/294 ALSA: sh: aica: reorder cleanup operations to avoid UAF bugs
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Duoming Zhou <[email protected]>
commit 051e0840ffa8ab25554d6b14b62c9ab9e4901457 upstream.
The dreamcastcard->timer could schedule the spu_dma_work and the spu_dma_work could also arm the dreamcastcard->timer.
When the snd_pcm_substream is closing, the aica_channel will be deallocated. But it could still be dereferenced in the worker thread. The reason is that del_timer() will return directly regardless of whether the timer handler is running or not and the worker could be rescheduled in the timer handler. As a result, the UAF bug will happen. The racy situation is shown below:
(Thread 1) | (Thread 2)
snd_aicapcm_pcm_close() |
... | run_spu_dma() //worker
| mod_timer()
flush_work() |
del_timer() | aica_period_elapsed() //timer
kfree(dreamcastcard->channel) | schedule_work()
| run_spu_dma() //worker
... | dreamcastcard->channel-> //USEIn order to mitigate this bug and other possible corner cases, call mod_timer() conditionally in run_spu_dma(), then implement PCM sync_stop op to cancel both the timer and worker. The sync_stop op will be called from PCM core appropriately when needed.
Message-ID: <[email protected]>
--- sound/sh/aica.c | 17 ++++++++++++++--- 1 file changed, 14 insertions(+), 3 deletions(-)
sound/sh/aica.c +14 -3
@@ -279,7 +279,8 @@ static void run_spu_dma(struct work_stru dreamcastcard->clicks++;if (unlikely (dreamcastcard->clicks >=AICA_PERIOD_NUMBER )) dreamcastcard->clicks %=AICA_PERIOD_NUMBER ; -mod_timer (&dreamcastcard->timer, jiffies +1 ); +if (snd_pcm_running (dreamcastcard->substream)) +mod_timer (&dreamcastcard->timer, jiffies +1 ); } }
@@ -291,6 +292,8 @@ static void aica_period_elapsed(struct t/*timer function - so cannot sleep */ int play_period;struct snd_pcm_runtime *runtime; +if (!snd_pcm_running (substream)) +return ; runtime = substream->runtime; dreamcastcard = substream->pcm->private_data;/* Have we played out an additional period? */
@@ -351,12 +354,19 @@ static int snd_aicapcm_pcm_open(struct sreturn 0 ; } +static int snd_aicapcm_pcm_sync_stop (struct snd_pcm_substream *substream) +{ +struct snd_card_aica *dreamcastcard = substream->pcm->private_data; + +del_timer_sync (&dreamcastcard->timer); +cancel_work_sync (&dreamcastcard->spu_dma_work); +return 0 ; +} +static int snd_aicapcm_pcm_close (struct snd_pcm_substream *substream) {struct snd_card_aica *dreamcastcard = substream->pcm->private_data; -flush_work (&(dreamcastcard->spu_dma_work)); -del_timer (&dreamcastcard->timer); dreamcastcard->substream =NULL ;kfree (dreamcastcard->channel);spu_disable ();
@@ -402,6 +412,7 @@ static const struct snd_pcm_ops snd_aica .prepare = snd_aicapcm_pcm_prepare, .trigger = snd_aicapcm_pcm_trigger, .pointer = snd_aicapcm_pcm_pointer, + .sync_stop = snd_aicapcm_pcm_sync_stop, };/* TO DO: set up to handle more than one pcm instance */
Greg Kroah-Hartman
maintainerPATCH 164/294 scsi: core: Fix unremoved procfs host directory regression
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Guilherme G. Piccoli <[email protected]>
commit f23a4d6e07570826fe95023ca1aa96a011fa9f84 upstream.
Commit fc663711b944 ("scsi: core: Remove the /proc/scsi/${proc_name} directory earlier") fixed a bug related to modules loading/unloading, by adding a call to scsi_proc_hostdir_rm() on scsi_remove_host(). But that led to a potential duplicate call to the hostdir_rm() routine, since it's also called from scsi_host_dev_release(). That triggered a regression report, which was then fixed by commit be03df3d4bfe ("scsi: core: Fix a procfs host directory removal regression"). The fix just dropped the hostdir_rm() call from dev_release().
But it happens that this proc directory is created on scsi_host_alloc(), and that function "pairs" with scsi_host_dev_release(), while scsi_remove_host() pairs with scsi_add_host(). In other words, it seems the reason for removing the proc directory on dev_release() was meant to cover cases in which a SCSI host structure was allocated, but the call to scsi_add_host() didn't happen. And that pattern happens to exist in some error paths, for example.
Syzkaller causes that by using USB raw gadget device, error'ing on usb-storage driver, at usb_stor_probe2(). By checking that path, we can see that the BadDevice label leads to a scsi_host_put() after a SCSI host allocation, but there's no call to scsi_add_host() in such path. That leads to messages like this in dmesg (and a leak of the SCSI host proc structure):
usb-storage 4-1:87.51: USB Mass Storage device detected proc_dir_entry 'scsi/usb-storage' already registered
WARNING: CPU: 1 PID: 3519 at fs/proc/generic.c:377 proc_register+0x347/0x4e0 fs/proc/generic.c:376
The proper fix seems to still call scsi_proc_hostdir_rm() on dev_release(), but guard that with the state check for SHOST_CREATED; there is even a comment in scsi_host_dev_release() detailing that: such conditional is meant for cases where the SCSI host was allocated but there was no calls to {add,remove}_host(), like the usb-storage case.
This is what we propose here and with that, the error path of usb-storage does not trigger the warning anymore.
--- drivers/scsi/hosts.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/scsi/hosts.c +4 -3
@@ -334,12 +334,13 @@ static void scsi_host_dev_release(structif (shost->shost_state ==SHOST_CREATED ) {/* -* Free the shost_dev device name here if scsi_host_alloc() -* and scsi_host_put() have been called but neither +* Free the shost_dev device name and remove the proc host dir +* here if scsi_host_{alloc,put}() have been called but neither * scsi_host_add() nor scsi_host_remove() has been called. * This avoids that the memory allocated for the shost_dev -* name is leaked. +* name as well as the proc dir structure are leaked. */ +scsi_proc_hostdir_rm (shost->hostt);kfree (dev_name (&shost->shost_dev)); }
Greg Kroah-Hartman
maintainerPATCH 165/294 staging: vc04_services: changen strncpy() to strscpy_pad()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
commit ef25725b7f8aaffd7756974d3246ec44fae0a5cf upstream.
gcc-14 warns about this strncpy() that results in a non-terminated string for an overflow:
In file included from include/linux/string.h:369,
from drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c:20:
In function 'strncpy',
inlined from 'create_component' at drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c:940:2:include/linux/fortify-string.h:108:33: error: '__builtin_strncpy' specified bound 128 equals destination size [-Werror=stringop-truncation]
Change it to strscpy_pad(), which produces a properly terminated and zero-padded string.
--- drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c +2 -2
@@ -940,8 +940,8 @@ static int create_component(struct vchiq/* build component create message */ m.h.type =MMAL_MSG_TYPE_COMPONENT_CREATE ; m.u.component_create.client_component = component->client_component; -strncpy (m.u.component_create.name, name, -sizeof (m.u.component_create.name)); +strscpy_pad (m.u.component_create.name, name, +sizeof (m.u.component_create.name)); ret = send_synchronous_mmal_msg(instance, &m, sizeof(m.u.component_create),
Greg Kroah-Hartman
maintainerPATCH 166/294 staging: vc04_services: fix information leak in create_component()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dan Carpenter <[email protected]>
commit f37e76abd614b68987abc8e5c22d986013349771 upstream.
The m.u.component_create.pid field is for debugging and in the mainline kernel it's not used anything. However, it still needs to be set to something to prevent disclosing uninitialized stack data. Set it to zero.
--- drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c | 1 + 1 file changed, 1 insertion(+)
drivers/staging/vc04_services/vchiq-mmal/mmal-vchiq.c +1 -0
@@ -942,6 +942,7 @@ static int create_component(struct vchiq m.u.component_create.client_component = component->client_component;strscpy_pad (m.u.component_create.name, name,sizeof (m.u.component_create.name)); + m.u.component_create.pid =0 ; ret = send_synchronous_mmal_msg(instance, &m, sizeof(m.u.component_create),
Greg Kroah-Hartman
maintainerPATCH 167/294 USB: core: Add hub_get() and hub_put() routines
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alan Stern <[email protected]>
commit ee113b860aa169e9a4d2c167c95d0f1961c6e1b8 upstream.
Create hub_get() and hub_put() routines to encapsulate the kref_get() and kref_put() calls in hub.c. The new routines will be used by the next patch in this series.
--- drivers/usb/core/hub.c | 23 ++++++++++++++++------- drivers/usb/core/hub.h | 2 ++ 2 files changed, 18 insertions(+), 7 deletions(-)
drivers/usb/core/hub.c +16 -7
@@ -116,7 +116,6 @@ EXPORT_SYMBOL_GPL(ehci_cf_port_reset_rws#define HUB_DEBOUNCE_STEP 25#define HUB_DEBOUNCE_STABLE 100 -static void hub_release (struct kref *kref);static int usb_reset_and_verify_device (struct usb_device *udev);static int hub_port_disable (struct usb_hub *hub,int port1,int set_state); static bool hub_port_warm_reset_required(struct usb_hub *hub, int port1,
@@ -678,14 +677,14 @@ static void kick_hub_wq(struct usb_hub **/ intf =to_usb_interface (hub->intfdev);usb_autopm_get_interface_no_resume (intf); -kref_get (&hub->kref); +hub_get (hub);if (queue_work (hub_wq, &hub->events))return ;/* the work has already been scheduled */ usb_autopm_put_interface_async (intf); -kref_put (&hub->kref, hub_release); +hub_put (hub); }void usb_kick_hub_wq (struct usb_device *hdev)
@@ -1053,7 +1052,7 @@ static void hub_activate(struct usb_hub goto init2; goto init3; } -kref_get (&hub->kref); +hub_get (hub);/* The superspeed hub except for root hub has to use Hub Depth * value as an offset into the route string to locate the bits
@@ -1301,7 +1300,7 @@ static void hub_activate(struct usb_hubdevice_unlock (&hdev->dev); } -kref_put (&hub->kref, hub_release); +hub_put (hub); }/* Implement the continuations for the delays above */
@@ -1717,6 +1716,16 @@ static void hub_release(struct kref *krekfree (hub); } +void hub_get (struct usb_hub *hub) +{ +kref_get (&hub->kref); +} + +void hub_put (struct usb_hub *hub) +{ +kref_put (&hub->kref, hub_release); +} +static unsigned highspeed_hubs;static void hub_disconnect (struct usb_interface *intf)
@@ -1763,7 +1772,7 @@ static void hub_disconnect(struct usb_inif (hub->quirk_disable_autosuspend)usb_autopm_put_interface (intf); -kref_put (&hub->kref, hub_release); +hub_put (hub); }static bool hub_descriptor_is_sane (struct usb_host_interface *desc)
@@ -5857,7 +5866,7 @@ out_hdev_lock:/* Balance the stuff in kick_hub_wq() and allow autosuspend */ usb_autopm_put_interface (intf); -kref_put (&hub->kref, hub_release); +hub_put (hub);kcov_remote_stop (); }
drivers/usb/core/hub.h +2 -0
@@ -117,6 +117,8 @@ extern void usb_hub_remove_port_device(sextern int usb_hub_set_port_power (struct usb_device *hdev,struct usb_hub *hub,int port1,bool set);extern struct usb_hub *usb_hub_to_struct_hub (struct usb_device *hdev); +extern void hub_get (struct usb_hub *hub); +extern void hub_put (struct usb_hub *hub);extern int hub_port_debounce (struct usb_hub *hub,int port1,bool must_be_connected); extern int usb_clear_port_feature(struct usb_device *hdev,
Greg Kroah-Hartman
maintainerPATCH 168/294 usb: dwc2: host: Fix remote wakeup from hibernation
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Minas Harutyunyan <[email protected]>
commit bae2bc73a59c200db53b6c15fb26bb758e2c6108 upstream.
Starting from core v4.30a changed order of programming GPWRDN_PMUACTV to 0 in case of exit from hibernation on remote wakeup signaling from device.
--- drivers/usb/dwc2/core.h | 1 + drivers/usb/dwc2/hcd.c | 17 +++++++++++++---- 2 files changed, 14 insertions(+), 4 deletions(-)
drivers/usb/dwc2/core.h +1 -0
@@ -1097,6 +1097,7 @@ struct dwc2_hsotg {bool needs_byte_swap;/* DWC OTG HW Release versions */ +#define DWC2_CORE_REV_4_30a 0x4f54430a#define DWC2_CORE_REV_2_71a 0x4f54271a#define DWC2_CORE_REV_2_72a 0x4f54272a#define DWC2_CORE_REV_2_80a 0x4f54280a
drivers/usb/dwc2/hcd.c +13 -4
@@ -5523,10 +5523,12 @@ int dwc2_host_exit_hibernation(struct dwdwc2_writel (hsotg, hr->hcfg,HCFG );/* De-assert Wakeup Logic */ - gpwrdn =dwc2_readl (hsotg,GPWRDN ); - gpwrdn &= ~GPWRDN_PMUACTV ; -dwc2_writel (hsotg, gpwrdn,GPWRDN ); -udelay (10 ); +if (!(rem_wakeup && hsotg->hw_params.snpsid >= DWC2_CORE_REV_4_30a)) { + gpwrdn =dwc2_readl (hsotg,GPWRDN ); + gpwrdn &= ~GPWRDN_PMUACTV ; +dwc2_writel (hsotg, gpwrdn,GPWRDN ); +udelay (10 ); + } hprt0 = hr->hprt0; hprt0 |=HPRT0_PWR ;
@@ -5551,6 +5553,13 @@ int dwc2_host_exit_hibernation(struct dw hprt0 |=HPRT0_RES ;dwc2_writel (hsotg, hprt0,HPRT0 ); +/* De-assert Wakeup Logic */ +if ((rem_wakeup && hsotg->hw_params.snpsid >= DWC2_CORE_REV_4_30a)) { + gpwrdn =dwc2_readl (hsotg,GPWRDN ); + gpwrdn &= ~GPWRDN_PMUACTV ; +dwc2_writel (hsotg, gpwrdn,GPWRDN ); +udelay (10 ); + }/* Wait for Resume time and then program HPRT again */ mdelay (100 ); hprt0 &= ~HPRT0_RES ;
Greg Kroah-Hartman
maintainerPATCH 169/294 usb: dwc2: host: Fix hibernation flow
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Minas Harutyunyan <[email protected]>
commit 3c7b9856a82227db01a20171d2e24c7ce305d59b upstream.
Added to backup/restore registers HFLBADDR, HCCHARi, HCSPLTi, HCTSIZi, HCDMAi and HCDMABi.
--- drivers/usb/dwc2/core.h | 12 ++++++++++++ drivers/usb/dwc2/hcd.c | 18 ++++++++++++++++-- 2 files changed, 28 insertions(+), 2 deletions(-)
drivers/usb/dwc2/core.h +12 -0
@@ -748,8 +748,14 @@ struct dwc2_dregs_backup {* struct dwc2_hregs_backup - Holds host registers state before * entering partial power down * @hcfg: Backup of HCFG register +* @hflbaddr: Backup of HFLBADDR register * @haintmsk: Backup of HAINTMSK register +* @hcchar: Backup of HCCHAR register +* @hcsplt: Backup of HCSPLT register * @hcintmsk: Backup of HCINTMSK register +* @hctsiz: Backup of HCTSIZ register +* @hdma: Backup of HCDMA register +* @hcdmab: Backup of HCDMAB register * @hprt0: Backup of HPTR0 register * @hfir: Backup of HFIR register * @hptxfsiz: Backup of HPTXFSIZ register
@@ -757,8 +763,14 @@ struct dwc2_dregs_backup {*/ struct dwc2_hregs_backup {u32 hcfg; +u32 hflbaddr;u32 haintmsk; +u32 hcchar[MAX_EPS_CHANNELS ]; +u32 hcsplt[MAX_EPS_CHANNELS ];u32 hcintmsk[MAX_EPS_CHANNELS ]; +u32 hctsiz[MAX_EPS_CHANNELS ]; +u32 hcidma[MAX_EPS_CHANNELS ]; +u32 hcidmab[MAX_EPS_CHANNELS ];u32 hprt0;u32 hfir;u32 hptxfsiz;
drivers/usb/dwc2/hcd.c +16 -2
@@ -5319,9 +5319,16 @@ int dwc2_backup_host_registers(struct dw/* Backup Host regs */ hr = &hsotg->hr_backup; hr->hcfg =dwc2_readl (hsotg,HCFG ); + hr->hflbaddr =dwc2_readl (hsotg,HFLBADDR ); hr->haintmsk =dwc2_readl (hsotg,HAINTMSK ); -for (i =0 ; i < hsotg->params.host_channels; ++i) +for (i =0 ; i < hsotg->params.host_channels; ++i) { + hr->hcchar[i] =dwc2_readl (hsotg,HCCHAR (i)); + hr->hcsplt[i] =dwc2_readl (hsotg,HCSPLT (i)); hr->hcintmsk[i] =dwc2_readl (hsotg,HCINTMSK (i)); + hr->hctsiz[i] =dwc2_readl (hsotg,HCTSIZ (i)); + hr->hcidma[i] =dwc2_readl (hsotg,HCDMA (i)); + hr->hcidmab[i] =dwc2_readl (hsotg,HCDMAB (i)); + } hr->hprt0 =dwc2_read_hprt0 (hsotg); hr->hfir =dwc2_readl (hsotg,HFIR );
@@ -5355,10 +5362,17 @@ int dwc2_restore_host_registers(struct d hr->valid = false;dwc2_writel (hsotg, hr->hcfg,HCFG ); +dwc2_writel (hsotg, hr->hflbaddr,HFLBADDR );dwc2_writel (hsotg, hr->haintmsk,HAINTMSK ); -for (i =0 ; i < hsotg->params.host_channels; ++i) +for (i =0 ; i < hsotg->params.host_channels; ++i) { +dwc2_writel (hsotg, hr->hcchar[i],HCCHAR (i)); +dwc2_writel (hsotg, hr->hcsplt[i],HCSPLT (i));dwc2_writel (hsotg, hr->hcintmsk[i],HCINTMSK (i)); +dwc2_writel (hsotg, hr->hctsiz[i],HCTSIZ (i)); +dwc2_writel (hsotg, hr->hcidma[i],HCDMA (i)); +dwc2_writel (hsotg, hr->hcidmab[i],HCDMAB (i)); + }dwc2_writel (hsotg, hr->hprt0,HPRT0 );dwc2_writel (hsotg, hr->hfir,HFIR );
Greg Kroah-Hartman
maintainerPATCH 170/294 usb: dwc2: host: Fix ISOC flow in DDMA mode
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Minas Harutyunyan <[email protected]>
commit b258e42688501cadb1a6dd658d6f015df9f32d8f upstream.
Fixed ISOC completion flow in DDMA mode. Added isoc descriptor actual length value and update urb's start_frame value.
Fixed initialization of ISOC DMA descriptors flow.
--- drivers/usb/dwc2/hcd.c | 12 ++++++++++-- drivers/usb/dwc2/hcd_ddma.c | 17 +++++++++++------ drivers/usb/dwc2/hw.h | 2 +- 3 files changed, 22 insertions(+), 9 deletions(-)
drivers/usb/dwc2/hcd.c +10 -2
@@ -2736,8 +2736,11 @@ enum dwc2_transaction_type dwc2_hcd_sele hsotg->available_host_channels--; } qh = list_entry(qh_ptr, struct dwc2_qh, qh_list_entry); -if (dwc2_assign_and_init_hc (hsotg, qh)) +if (dwc2_assign_and_init_hc (hsotg, qh)) { +if (hsotg->params.uframe_sched) + hsotg->available_host_channels++;break ; + }/* * Move the QH from the periodic ready schedule to the
@@ -2770,8 +2773,11 @@ enum dwc2_transaction_type dwc2_hcd_sele hsotg->available_host_channels--; } -if (dwc2_assign_and_init_hc (hsotg, qh)) +if (dwc2_assign_and_init_hc (hsotg, qh)) { +if (hsotg->params.uframe_sched) + hsotg->available_host_channels++;break ; + }/* * Move the QH from the non-periodic inactive schedule to the
@@ -4125,6 +4131,8 @@ void dwc2_host_complete(struct dwc2_hsot urb->actual_length);if (usb_pipetype (urb->pipe) ==PIPE_ISOCHRONOUS ) { +if (!hsotg->params.dma_desc_enable) + urb->start_frame = qtd->qh->start_active_frame; urb->error_count =dwc2_hcd_urb_get_error_count (qtd->urb);for (i =0 ; i < urb->number_of_packets; ++i) { urb->iso_frame_desc[i].actual_length =
drivers/usb/dwc2/hcd_ddma.c +11 -6
@@ -589,7 +589,7 @@ static void dwc2_init_isoc_dma_desc(stru idx = qh->td_last; inc = qh->host_interval; hsotg->frame_number =dwc2_hcd_get_frame_number (hsotg); - cur_idx =dwc2_frame_list_idx (hsotg->frame_number); + cur_idx = idx; next_idx =dwc2_desclist_idx_inc (qh->td_last, inc, qh->dev_speed);/*
@@ -896,6 +896,8 @@ static int dwc2_cmpl_host_isoc_dma_desc( {struct dwc2_dma_desc *dma_desc;struct dwc2_hcd_iso_packet_desc *frame_desc; +u16 frame_desc_idx; +struct urb *usb_urb = qtd->urb->priv;u16 remain =0 ;int rc =0 ;
@@ -908,8 +910,11 @@ static int dwc2_cmpl_host_isoc_dma_desc( DMA_FROM_DEVICE); dma_desc = &qh->desc_list[idx]; + frame_desc_idx = (idx - qtd->isoc_td_first) & (usb_urb->number_of_packets -1 ); - frame_desc = &qtd->urb->iso_descs[qtd->isoc_frame_index_last]; + frame_desc = &qtd->urb->iso_descs[frame_desc_idx]; +if (idx == qtd->isoc_td_first) + usb_urb->start_frame =dwc2_hcd_get_frame_number (hsotg); dma_desc->buf = (u32)(qtd->urb->dma + frame_desc->offset);if (chan->ep_is_in) remain = (dma_desc->status & HOST_DMA_ISOC_NBYTES_MASK) >>
@@ -930,7 +935,7 @@ static int dwc2_cmpl_host_isoc_dma_desc( frame_desc->status =0 ; } -if (++qtd->isoc_frame_index == qtd->urb->packet_count) { +if (++qtd->isoc_frame_index == usb_urb->number_of_packets) {/* * urb->status is not used for isoc transfers here. The * individual frame_desc status are used instead.
@@ -1035,11 +1040,11 @@ static void dwc2_complete_isoc_xfer_ddmareturn ; idx =dwc2_desclist_idx_inc (idx, qh->host_interval, chan->speed); -if (!rc) +if (rc ==0 )continue ; -if (rc ==DWC2_CMPL_DONE ) -break ; +if (rc ==DWC2_CMPL_DONE || rc ==DWC2_CMPL_STOP ) + goto stop_scan;/* rc == DWC2_CMPL_STOP */
drivers/usb/dwc2/hw.h +1 -1
@@ -727,7 +727,7 @@#define TXSTS_QTOP_TOKEN_MASK (0x3 << 25)#define TXSTS_QTOP_TOKEN_SHIFT 25#define TXSTS_QTOP_TERMINATE BIT(24) -#define TXSTS_QSPCAVAIL_MASK (0xff << 16) +#define TXSTS_QSPCAVAIL_MASK (0x7f << 16)#define TXSTS_QSPCAVAIL_SHIFT 16#define TXSTS_FSPCAVAIL_MASK (0xffff << 0)#define TXSTS_FSPCAVAIL_SHIFT 0
Greg Kroah-Hartman
maintainerPATCH 171/294 usb: dwc2: gadget: LPM flow fix
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Minas Harutyunyan <[email protected]>
commit 5d69a3b54e5a630c90d82a4c2bdce3d53dc78710 upstream.
Added functionality to exit from L1 state by device initiation using remote wakeup signaling, in case when function driver queuing request while core in L1 state.
--- drivers/usb/dwc2/core.h | 1 drivers/usb/dwc2/core_intr.c | 65 ++++++++++++++++++++++++++++--------------- drivers/usb/dwc2/gadget.c | 4 ++ 3 files changed, 48 insertions(+), 22 deletions(-)
drivers/usb/dwc2/core.h +1 -0
@@ -1348,6 +1348,7 @@ int dwc2_backup_global_registers(structint dwc2_restore_global_registers (struct dwc2_hsotg *hsotg);void dwc2_enable_acg (struct dwc2_hsotg *hsotg); +void dwc2_wakeup_from_lpm_l1 (struct dwc2_hsotg *hsotg,bool remotewakeup);/* This function should be called on every hardware interrupt. */ irqreturn_t dwc2_handle_common_intr (int irq,void *dev);
drivers/usb/dwc2/core_intr.c +43 -22
97 lines not on this page · raw message
drivers/usb/dwc2/gadget.c +4 -0
@@ -1416,6 +1416,10 @@ static int dwc2_hsotg_ep_queue(struct us ep->name, req, req->length, req->buf, req->no_interrupt, req->zero, req->short_not_ok); +if (hs->lx_state ==DWC2_L1 ) { +dwc2_wakeup_from_lpm_l1 (hs, true); + } +/* Prevent new request submission when controller is suspended */ if (hs->lx_state !=DWC2_L0 ) { dev_dbg(hs->dev, "%s: submit request only in active state\n",
Greg Kroah-Hartman
maintainerPATCH 172/294 usb: udc: remove warning when queue disabled ep
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: yuan linyu <[email protected]>
commit 2a587a035214fa1b5ef598aea0b81848c5b72e5e upstream.
It is possible trigger below warning message from mass storage function,
WARNING: CPU: 6 PID: 3839 at drivers/usb/gadget/udc/core.c:294 usb_ep_queue+0x7c/0x104 pc : usb_ep_queue+0x7c/0x104 lr : fsg_main_thread+0x494/0x1b3c
Root cause is mass storage function try to queue request from main thread, but other thread may already disable ep when function disable.
As there is no function failure in the driver, in order to avoid effort to fix warning, change WARN_ON_ONCE() in usb_ep_queue() to pr_debug().
--- drivers/usb/gadget/udc/core.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/usb/gadget/udc/core.c +3 -1
@@ -273,7 +273,9 @@ int usb_ep_queue(struct usb_ep *ep, {int ret =0 ; -if (WARN_ON_ONCE (!ep->enabled && ep->address)) { +if (!ep->enabled && ep->address) { +pr_debug ("USB gadget: queue request to disabled ep 0x%x (%s)\n" , + ep->address, ep->name); ret = -ESHUTDOWN ; goto out; }
Greg Kroah-Hartman
maintainerPATCH 173/294 usb: typec: ucsi: Ack unsupported commands
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Christian A. Ehrhardt <[email protected]>
commit 6b5c85ddeea77d18c4b69e3bda60e9374a20c304 upstream.
If a command completes the OPM must send an ack. This applies to unsupported commands, too.
Send the required ACK for unsupported commands.
--- drivers/usb/typec/ucsi/ucsi.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/usb/typec/ucsi/ucsi.c +5 -1
@@ -138,8 +138,12 @@ static int ucsi_exec_command(struct ucsiif (!(cci &UCSI_CCI_COMMAND_COMPLETE ))return -EIO ; -if (cci &UCSI_CCI_NOT_SUPPORTED ) +if (cci &UCSI_CCI_NOT_SUPPORTED ) { +if (ucsi_acknowledge_command (ucsi) <0 ) +dev_err (ucsi->dev, +"ACK of unsupported command failed\n" );return -EOPNOTSUPP ; + }if (cci &UCSI_CCI_ERROR ) {if (cmd ==UCSI_GET_ERROR_STATUS )
Greg Kroah-Hartman
maintainerPATCH 174/294 usb: typec: ucsi: Clear UCSI_CCI_RESET_COMPLETE before reset
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Christian A. Ehrhardt <[email protected]>
commit 3de4f996a0b5412aa451729008130a488f71563e upstream.
Check the UCSI_CCI_RESET_COMPLETE complete flag before starting another reset. Use a UCSI_SET_NOTIFICATION_ENABLE command to clear the flag if it is set.
--- drivers/usb/typec/ucsi/ucsi.c | 36 +++++++++++++++++++++++++++++++++++- 1 file changed, 35 insertions(+), 1 deletion(-)
drivers/usb/typec/ucsi/ucsi.c +35 -1
@@ -852,13 +852,47 @@ static int ucsi_reset_connector(struct ustatic int ucsi_reset_ppm (struct ucsi *ucsi) { -u64 command =UCSI_PPM_RESET ; +u64 command;unsigned long tmo;u32 cci;int ret;mutex_lock (&ucsi->ppm_lock); + ret = ucsi->ops->read (ucsi,UCSI_CCI , &cci,sizeof (cci)); +if (ret <0 ) + goto out; + +/* +* If UCSI_CCI_RESET_COMPLETE is already set we must clear +* the flag before we start another reset. Send a +* UCSI_SET_NOTIFICATION_ENABLE command to achieve this. +* Ignore a timeout and try the reset anyway if this fails. +*/ +if (cci &UCSI_CCI_RESET_COMPLETE ) { + command =UCSI_SET_NOTIFICATION_ENABLE ; + ret = ucsi->ops->async_write (ucsi,UCSI_CONTROL , &command, +sizeof (command)); +if (ret <0 ) + goto out; + + tmo = jiffies +msecs_to_jiffies (UCSI_TIMEOUT_MS ); +do { + ret = ucsi->ops->read (ucsi,UCSI_CCI , + &cci,sizeof (cci)); +if (ret <0 ) + goto out; +if (cci &UCSI_CCI_COMMAND_COMPLETE ) +break ; +if (time_is_before_jiffies (tmo)) +break ; +msleep (20 ); + }while (1 ); + +WARN_ON (cci &UCSI_CCI_RESET_COMPLETE ); + } + + command =UCSI_PPM_RESET ; ret = ucsi->ops->async_write (ucsi,UCSI_CONTROL , &command,sizeof (command));if (ret <0 )
Greg Kroah-Hartman
maintainerPATCH 175/294 scsi: qla2xxx: Split FCE|EFT trace control
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Quinn Tran <[email protected]>
commit 76a192e1a566e15365704b9f8fb3b70825f85064 upstream.
Current code combines the allocation of FCE|EFT trace buffers and enables the features all in 1 step.
Split this step into separate steps in preparation for follow-on patch to allow user to have a choice to enable / disable FCE trace feature.
--- drivers/scsi/qla2xxx/qla_init.c | 102 ++++++++++++++++------------------------ 1 file changed, 41 insertions(+), 61 deletions(-)
drivers/scsi/qla2xxx/qla_init.c +41 -61
@@ -2280,6 +2280,40 @@ exit:return rval; } +static void qla_enable_fce_trace (scsi_qla_host_t *vha) +{ +int rval; +struct qla_hw_data *ha = vha->hw; + +if (ha->fce) { + ha->flags.fce_enabled =1 ; +memset (ha->fce,0 ,fce_calc_size (ha->fce_bufs)); + rval =qla2x00_enable_fce_trace (vha, + ha->fce_dma, ha->fce_bufs, ha->fce_mb, &ha->fce_bufs); + +if (rval) { +ql_log (ql_log_warn, vha,0x8033 , +"Unable to reinitialize FCE (%d).\n" , rval); + ha->flags.fce_enabled =0 ; + } + } +} + +static void qla_enable_eft_trace (scsi_qla_host_t *vha) +{ +int rval; +struct qla_hw_data *ha = vha->hw; + +if (ha->eft) { +memset (ha->eft,0 ,EFT_SIZE ); + rval =qla2x00_enable_eft_trace (vha, ha->eft_dma,EFT_NUM_BUFFERS ); + +if (rval) { +ql_log (ql_log_warn, vha,0x8034 , +"Unable to reinitialize EFT (%d).\n" , rval); + } + } +}/* * qla2x00_initialize_adapter * Initialize board.
@@ -3230,9 +3264,8 @@ qla24xx_chip_diag(scsi_qla_host_t *vha) }static void -qla2x00_init_fce_trace (scsi_qla_host_t *vha) +qla2x00_alloc_fce_trace (scsi_qla_host_t *vha) { -int rval;dma_addr_t tc_dma;void *tc;struct qla_hw_data *ha = vha->hw;
@@ -3261,27 +3294,17 @@ qla2x00_init_fce_trace(scsi_qla_host_t *return ; } - rval =qla2x00_enable_fce_trace (vha, tc_dma,FCE_NUM_BUFFERS , - ha->fce_mb, &ha->fce_bufs); -if (rval) { -ql_log (ql_log_warn, vha,0x00bf , -"Unable to initialize FCE (%d).\n" , rval); -dma_free_coherent (&ha->pdev->dev,FCE_SIZE , tc, tc_dma); -return ; - } -ql_dbg (ql_dbg_init, vha,0x00c0 ,"Allocated (%d KB) for FCE...\n" ,FCE_SIZE /1024 ); - ha->flags.fce_enabled =1 ; ha->fce_dma = tc_dma; ha->fce = tc; + ha->fce_bufs =FCE_NUM_BUFFERS ; }static void -qla2x00_init_eft_trace (scsi_qla_host_t *vha) +qla2x00_alloc_eft_trace (scsi_qla_host_t *vha) { -int rval;dma_addr_t tc_dma;void *tc;struct qla_hw_data *ha = vha->hw;
@@ -3306,14 +3329,6 @@ qla2x00_init_eft_trace(scsi_qla_host_t *return ; } - rval =qla2x00_enable_eft_trace (vha, tc_dma,EFT_NUM_BUFFERS ); -if (rval) { -ql_log (ql_log_warn, vha,0x00c2 , -"Unable to initialize EFT (%d).\n" , rval); -dma_free_coherent (&ha->pdev->dev,EFT_SIZE , tc, tc_dma); -return ; - } -ql_dbg (ql_dbg_init, vha,0x00c3 ,"Allocated (%d KB) EFT ...\n" ,EFT_SIZE /1024 );
@@ -3321,13 +3336,6 @@ qla2x00_init_eft_trace(scsi_qla_host_t * ha->eft = tc; } -static void -qla2x00_alloc_offload_mem (scsi_qla_host_t *vha) -{ -qla2x00_init_fce_trace (vha); -qla2x00_init_eft_trace (vha); -} -void qla2x00_alloc_fw_dump (scsi_qla_host_t *vha) {
@@ -3382,10 +3390,10 @@ qla2x00_alloc_fw_dump(scsi_qla_host_t *vif (ha->tgt.atio_ring) mq_size += ha->tgt.atio_q_length *sizeof (request_t); -qla2x00_init_fce_trace (vha); +qla2x00_alloc_fce_trace (vha);if (ha->fce) fce_size =sizeof (struct qla2xxx_fce_chain ) +FCE_SIZE ; -qla2x00_init_eft_trace (vha); +qla2x00_alloc_eft_trace (vha);if (ha->eft) eft_size =EFT_SIZE ; }
@@ -3784,7 +3792,6 @@ qla2x00_setup_chip(scsi_qla_host_t *vha)struct qla_hw_data *ha = vha->hw;struct device_reg_2xxx __iomem *reg = &ha->iobase->isp;unsigned long flags; -uint16_t fw_major_version;int done_once =0 ;if (IS_P3P_TYPE (ha)) {
@@ -3851,7 +3858,6 @@ execute_fw_with_lr: goto failed; enable_82xx_npiv: - fw_major_version = ha->fw_major_version;if (IS_P3P_TYPE (ha))qla82xx_check_md_needed (vha);else
@@ -3880,12 +3886,11 @@ enable_82xx_npiv:if (rval !=QLA_SUCCESS ) goto failed; -if (!fw_major_version && !(IS_P3P_TYPE (ha))) -qla2x00_alloc_offload_mem (vha); -if (ql2xallocfwdump && !(IS_P3P_TYPE (ha)))qla2x00_alloc_fw_dump (vha); +qla_enable_fce_trace (vha); +qla_enable_eft_trace (vha); }else { goto failed; }
@@ -7012,7 +7017,6 @@ qla2x00_abort_isp_cleanup(scsi_qla_host_int qla2x00_abort_isp (scsi_qla_host_t *vha) { -int rval;uint8_t status =0 ;struct qla_hw_data *ha = vha->hw;struct scsi_qla_host *vp;
@@ -7100,31 +7104,7 @@ qla2x00_abort_isp(scsi_qla_host_t *vha)if (IS_QLA81XX (ha) ||IS_QLA8031 (ha))qla2x00_get_fw_version (vha); -if (ha->fce) { - ha->flags.fce_enabled =1 ; -memset (ha->fce,0 , -fce_calc_size (ha->fce_bufs)); - rval =qla2x00_enable_fce_trace (vha, - ha->fce_dma, ha->fce_bufs, ha->fce_mb, - &ha->fce_bufs); -if (rval) { -ql_log (ql_log_warn, vha,0x8033 , -"Unable to reinitialize FCE " -"(%d).\n" , rval); - ha->flags.fce_enabled =0 ; - } - } -if (ha->eft) { -memset (ha->eft,0 ,EFT_SIZE ); - rval =qla2x00_enable_eft_trace (vha, - ha->eft_dma,EFT_NUM_BUFFERS ); -if (rval) { -ql_log (ql_log_warn, vha,0x8034 , -"Unable to reinitialize EFT " -"(%d).\n" , rval); - } - } }else {/* failed the ISP abort */ vha->flags.online =1 ;if (test_bit (ISP_ABORT_RETRY , &vha->dpc_flags)) {
Greg Kroah-Hartman
maintainerPATCH 176/294 scsi: qla2xxx: Fix command flush on cable pull
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Quinn Tran <[email protected]>
commit a27d4d0e7de305def8a5098a614053be208d1aa1 upstream.
System crash due to command failed to flush back to SCSI layer.
BUG: unable to handle kernel NULL pointer dereference at 0000000000000000 PGD 0 P4D 0 Oops: 0000 [#1] SMP NOPTI CPU: 27 PID: 793455 Comm: kworker/u130:6 Kdump: loaded Tainted: G OE --------- - - 4.18.0-372.9.1.el8.x86_64 #1 Hardware name: HPE ProLiant DL360 Gen10/ProLiant DL360 Gen10, BIOS U32 09/03/2021 Workqueue: nvme-wq nvme_fc_connect_ctrl_work [nvme_fc] RIP: 0010:__wake_up_common+0x4c/0x190 Code: 24 10 4d 85 c9 74 0a 41 f6 01 04 0f 85 9d 00 00 00 48 8b 43 08 48 83 c3 08 4c 8d 48 e8 49 8d 41 18 48 39 c3 0f 84 f0 00 00 00 <49> 8b 41 18 89 54 24 08 31 ed 4c 8d 70 e8 45 8b 29 41 f6 c5 04 75 RSP: 0018:ffff95f3e0cb7cd0 EFLAGS: 00010086 RAX: 0000000000000000 RBX: ffff8b08d3b26328 RCX: 0000000000000000 RDX: 0000000000000001 RSI: 0000000000000003 RDI: ffff8b08d3b26320 RBP: 0000000000000001 R08: 0000000000000000 R09: ffffffffffffffe8 R10: 0000000000000000 R11: ffff95f3e0cb7a60 R12: ffff95f3e0cb7d20 R13: 0000000000000003 R14: 0000000000000000 R15: 0000000000000000 FS: 0000000000000000(0000) GS:ffff8b2fdf6c0000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000000000000 CR3: 0000002f1e410002 CR4: 00000000007706e0 DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 PKRU: 55555554 Call Trace: __wake_up_common_lock+0x7c/0xc0 qla_nvme_ls_req+0x355/0x4c0 [qla2xxx] qla2xxx [0000:12:00.1]-f084:3: qlt_free_session_done: se_sess 0000000000000000 / sess ffff8ae1407ca000 from port 21:32:00:02:ac:07:ee:b8 loop_id 0x02 s_id 01:02:00 logout 1 keep 0 els_logo 0 ? __nvme_fc_send_ls_req+0x260/0x380 [nvme_fc] qla2xxx [0000:12:00.1]-207d:3: FCPort 21:32:00:02:ac:07:ee:b8 state transitioned from ONLINE to LOST - portid=010200. ? nvme_fc_send_ls_req.constprop.42+0x1a/0x45 [nvme_fc] qla2xxx [0000:12:00.1]-2109:3: qla2x00_schedule_rport_del 21320002ac07eeb8. rport ffff8ae598122000 roles 1 ? nvme_fc_connect_ctrl_work.cold.63+0x1e3/0xa7d [nvme_fc] qla2xxx [0000:12:00.1]-f084:3: qlt_free_session_done: se_sess 0000000000000000 / sess ffff8ae14801e000 from port 21:32:01:02:ad:f7:ee:b8 loop_id 0x04 s_id 01:02:01 logout 1 keep 0 els_logo 0 ? __switch_to+0x10c/0x450 ? process_one_work+0x1a7/0x360 qla2xxx [0000:12:00.1]-207d:3: FCPort 21:32:01:02:ad:f7:ee:b8 state transitioned from ONLINE to LOST - portid=010201. ? worker_thread+0x1ce/0x390 ? create_worker+0x1a0/0x1a0 qla2xxx [0000:12:00.1]-2109:3: qla2x00_schedule_rport_del 21320102adf7eeb8. rport ffff8ae3b2312800 roles 70 ? kthread+0x10a/0x120 qla2xxx [0000:12:00.1]-2112:3: qla_nvme_unregister_remote_port: unregister remoteport on ffff8ae14801e000 21320102adf7eeb8 ? set_kthread_struct+0x40/0x40 qla2xxx [0000:12:00.1]-2110:3: remoteport_delete of ffff8ae14801e000 21320102adf7eeb8 completed. ? ret_from_fork+0x1f/0x40 qla2xxx [0000:12:00.1]-f086:3: qlt_free_session_done: waiting for sess ffff8ae14801e000 logout
The system was under memory stress where driver was not able to allocate an SRB to carry out error recovery of cable pull. The failure to flush causes upper layer to start modifying scsi_cmnd. When the system frees up some memory, the subsequent cable pull trigger another command flush. At this point the driver access a null pointer when attempting to DMA unmap the SGL.
Add a check to make sure commands are flush back on session tear down to prevent the null pointer access.
--- drivers/scsi/qla2xxx/qla_target.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
drivers/scsi/qla2xxx/qla_target.c +10 -0
@@ -1038,6 +1038,16 @@ void qlt_free_session_done(struct work_s "%s: sess %p logout completed\n", __func__, sess); } +/* check for any straggling io left behind */ +if (!(sess->flags &FCF_FCP2_DEVICE ) && +qla2x00_eh_wait_for_pending_commands (sess->vha, sess->d_id.b24,0 ,WAIT_TARGET )) { +ql_log (ql_log_warn, vha,0x3027 , +"IO not return. Resetting.\n" ); +set_bit (ISP_ABORT_NEEDED , &vha->dpc_flags); +qla2xxx_wake_dpc (vha); +qla2x00_wait_for_chip_reset (vha); + } +if (sess->logo_ack_needed) { sess->logo_ack_needed =0 ; qla24xx_async_notify_ack(vha, sess,
Greg Kroah-Hartman
maintainerPATCH 177/294 scsi: qla2xxx: Delay I/O Abort on PCI error
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Quinn Tran <[email protected]>
commit 591c1fdf2016d118b8fbde427b796fac13f3f070 upstream.
Currently when PCI error is detected, I/O is aborted manually through the ABORT IOCB mechanism which is not guaranteed to succeed.
Instead, wait for the OS or system to notify driver to wind down I/O through the pci_error_handlers api. Set eeh_busy flag to pause all traffic and wait for I/O to drain.
--- drivers/scsi/qla2xxx/qla_attr.c | 14 ++++++++++++-- 1 file changed, 12 insertions(+), 2 deletions(-)
drivers/scsi/qla2xxx/qla_attr.c +12 -2
@@ -2689,7 +2689,13 @@ qla2x00_dev_loss_tmo_callbk(struct fc_rpreturn ;if (unlikely (pci_channel_offline (fcport->vha->hw->pdev))) { -qla2x00_abort_all_cmds (fcport->vha,DID_NO_CONNECT <<16 ); +/* Will wait for wind down of adapter */ +ql_dbg (ql_dbg_aer, fcport->vha,0x900c , +"%s pci offline detected (id %06x)\n" , __func__, + fcport->d_id.b24); +qla_pci_set_eeh_busy (fcport->vha); +qla2x00_eh_wait_for_pending_commands (fcport->vha, fcport->d_id.b24, +0 ,WAIT_TARGET );return ; } }
@@ -2711,7 +2717,11 @@ qla2x00_terminate_rport_io(struct fc_rpo vha = fcport->vha;if (unlikely (pci_channel_offline (fcport->vha->hw->pdev))) { -qla2x00_abort_all_cmds (fcport->vha,DID_NO_CONNECT <<16 ); +/* Will wait for wind down of adapter */ +ql_dbg (ql_dbg_aer, fcport->vha,0x900b , +"%s pci offline detected (id %06x)\n" , __func__, + fcport->d_id.b24); +qla_pci_set_eeh_busy (vha);qla2x00_eh_wait_for_pending_commands (fcport->vha, fcport->d_id.b24,0 ,WAIT_TARGET );return ;
Greg Kroah-Hartman
maintainerPATCH 178/294 x86/cpu: Enable STIBP on AMD if Automatic IBRS is enabled
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kim Phillips <[email protected]>
commit fd470a8beed88440b160d690344fbae05a0b9b1b upstream.
Unlike Intel's Enhanced IBRS feature, AMD's Automatic IBRS does not provide protection to processes running at CPL3/user mode, see section "Extended Feature Enable Register (EFER)" in the APM v2 at
https://bugzilla.kernel.org/attachment.cgi?id=304652
Explicitly enable STIBP to protect against cross-thread CPL3 branch target injections on systems with Automatic IBRS enabled.
Also update the relevant documentation.
--- Documentation/admin-guide/hw-vuln/spectre.rst | 11 +++++++---- arch/x86/kernel/cpu/bugs.c | 15 +++++++++------ 2 files changed, 16 insertions(+), 10 deletions(-)
Documentation/admin-guide/hw-vuln/spectre.rst +7 -4
@@ -484,11 +484,14 @@ Spectre variant 2 Systems which support enhanced IBRS (eIBRS) enable IBRS protection once at boot, by setting the IBRS bit, and they're automatically protected against - Spectre v2 variant attacks, including cross-thread branch target injections - on SMT systems (STIBP). In other words, eIBRS enables STIBP too. + Spectre v2 variant attacks. - Legacy IBRS systems clear the IBRS bit on exit to userspace and - therefore explicitly enable STIBP for that + On Intel's enhanced IBRS systems, this includes cross-thread branch target + injections on SMT systems (STIBP). In other words, Intel eIBRS enables + STIBP, too. + + AMD Automatic IBRS does not protect userspace, and Legacy IBRS systems clear + the IBRS bit on exit to userspace, therefore both explicitly enable STIBP. The retpoline mitigation is turned on by default on vulnerable CPUs. It can be forced on or off by the administrator
arch/x86/kernel/cpu/bugs.c +9 -6
@@ -1317,19 +1317,21 @@ spectre_v2_user_select_mitigation(void) }/* -* If no STIBP, enhanced IBRS is enabled, or SMT impossible, STIBP +* If no STIBP, Intel enhanced IBRS is enabled, or SMT impossible, STIBP * is not required. * -* Enhanced IBRS also protects against cross-thread branch target +* Intel's Enhanced IBRS also protects against cross-thread branch target * injection in user-mode as the IBRS bit remains always set which * implicitly enables cross-thread protections. However, in legacy IBRS * mode, the IBRS bit is set only on kernel entry and cleared on return -* to userspace. This disables the implicit cross-thread protection, -* so allow for STIBP to be selected in that case. +* to userspace. AMD Automatic IBRS also does not protect userspace. +* These modes therefore disable the implicit cross-thread protection, +* so allow for STIBP to be selected in those cases. */ if (!boot_cpu_has (X86_FEATURE_STIBP ) || !smt_possible || -spectre_v2_in_eibrs_mode (spectre_v2_enabled)) + (spectre_v2_in_eibrs_mode (spectre_v2_enabled) && + !boot_cpu_has (X86_FEATURE_AUTOIBRS )))return ;/*
@@ -2596,7 +2598,8 @@ static ssize_t rfds_show_state(char *bufstatic char *stibp_state (void ) { -if (spectre_v2_in_eibrs_mode (spectre_v2_enabled)) +if (spectre_v2_in_eibrs_mode (spectre_v2_enabled) && + !boot_cpu_has (X86_FEATURE_AUTOIBRS ))return "" ;switch (spectre_v2_user_stibp) {
Greg Kroah-Hartman
maintainerPATCH 179/294 PCI/DPC: Quirk PIO log size for Intel Ice Lake Root Ports
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mika Westerberg <[email protected]>
commit 3b8803494a0612acdeee714cb72aa142b1e05ce5 upstream.
Commit 5459c0b70467 ("PCI/DPC: Quirk PIO log size for certain Intel Root Ports") added quirks for Tiger and Alder Lake Root Ports but missed that the same issue exists also in the previous generation, Ice Lake.
Apply the quirk for Ice Lake Root Ports as well. This prevents kernel complaints like:
DPC: RP PIO log size 0 is invalid
and also enables the DPC driver to dump the RP PIO Log registers when DPC is triggered.
--- drivers/pci/quirks.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-)
drivers/pci/quirks.c +7 -2
@@ -5912,8 +5912,9 @@ DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_I#ifdef CONFIG_PCIE_DPC /* -* Intel Tiger Lake and Alder Lake BIOS has a bug that clears the DPC -* RP PIO Log Size of the integrated Thunderbolt PCIe Root Ports. +* Intel Ice Lake, Tiger Lake and Alder Lake BIOS has a bug that clears +* the DPC RP PIO Log Size of the integrated Thunderbolt PCIe Root +* Ports. */ static void dpc_log_size (struct pci_dev *dev) {
@@ -5936,6 +5937,10 @@ DECLARE_PCI_FIXUP_HEADER(PCI_VENDOR_ID_IDECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x462f , dpc_log_size);DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x463f , dpc_log_size);DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x466e , dpc_log_size); +DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x8a1d , dpc_log_size); +DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x8a1f , dpc_log_size); +DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x8a21 , dpc_log_size); +DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x8a23 , dpc_log_size);DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x9a23 , dpc_log_size);DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x9a25 , dpc_log_size);DECLARE_PCI_FIXUP_HEADER (PCI_VENDOR_ID_INTEL ,0x9a27 , dpc_log_size);
Greg Kroah-Hartman
maintainerPATCH 180/294 scsi: lpfc: Correct size for wqe for memset()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Muhammad Usama Anjum <[email protected]>
commit 28d41991182c210ec1654f8af2e140ef4cc73f20 upstream.
The wqe is of type lpfc_wqe128. It should be memset with the same type.
--- drivers/scsi/lpfc/lpfc_nvmet.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/lpfc/lpfc_nvmet.c +1 -1
@@ -1579,7 +1579,7 @@ lpfc_nvmet_setup_io_context(struct lpfc_ wqe = &nvmewqe->wqe;/* Initialize WQE */ -memset (wqe,0 ,sizeof (union lpfc_wqe )); +memset (wqe,0 ,sizeof (*wqe)); ctx_buf->iocbq->context1 =NULL ;spin_lock (&phba->sli4_hba.sgl_list_lock);
Greg Kroah-Hartman
maintainerPATCH 181/294 USB: core: Fix deadlock in usb_deauthorize_interface()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alan Stern <[email protected]>
commit 80ba43e9f799cbdd83842fc27db667289b3150f5 upstream.
Among the attribute file callback routines in drivers/usb/core/sysfs.c, the interface_authorized_store() function is the only one which acquires a device lock on an ancestor device: It calls usb_deauthorize_interface(), which locks the interface's parent USB device.
The will lead to deadlock if another process already owns that lock and tries to remove the interface, whether through a configuration change or because the device has been disconnected. As part of the removal procedure, device_del() waits for all ongoing sysfs attribute callbacks to complete. But usb_deauthorize_interface() can't complete until the device lock has been released, and the lock won't be released until the removal has finished.
The mechanism provided by sysfs to prevent this kind of deadlock is to use the sysfs_break_active_protection() function, which tells sysfs not to wait for the attribute callback.
Reported-and-tested by: Yue Sun <[email protected]> Reported by: xingwei lee <[email protected]>
--- drivers/usb/core/sysfs.c | 16 +++++++++++++--- 1 file changed, 13 insertions(+), 3 deletions(-)
drivers/usb/core/sysfs.c +13 -3
@@ -1166,14 +1166,24 @@ static ssize_t interface_authorized_stor {struct usb_interface *intf =to_usb_interface (dev);bool val; +struct kernfs_node *kn;if (strtobool (buf, &val) !=0 )return -EINVAL ; -if (val) +if (val) {usb_authorize_interface (intf); -else -usb_deauthorize_interface (intf); + }else { +/* +* Prevent deadlock if another process is concurrently +* trying to unregister intf. +*/ + kn =sysfs_break_active_protection (&dev->kobj, &attr->attr); +if (kn) { +usb_deauthorize_interface (intf); +sysfs_unbreak_active_protection (kn); + } + }return count; }
Greg Kroah-Hartman
maintainerPATCH 182/294 nfc: nci: Fix uninit-value in nci_dev_up and nci_ntf_packet
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ryosuke Yasuoka <[email protected]>
[ Upstream commit d24b03535e5eb82e025219c2f632b485409c898f ]
syzbot reported the following uninit-value access issue [1][2]:
nci_rx_work() parses and processes received packet. When the payload length is zero, each message type handler reads uninitialized payload and KMSAN detects this issue. The receipt of a packet with a zero-size payload is considered unexpected, and therefore, such packets should be silently discarded.
This patch resolved this issue by checking payload size before calling each message type handler codes.
--- net/nfc/nci/core.c | 5 +++++ 1 file changed, 5 insertions(+)
net/nfc/nci/core.c +5 -0
@@ -1502,6 +1502,11 @@ static void nci_rx_work(struct work_struct *work)nfc_send_to_raw_sock (ndev->nfc_dev, skb,RAW_PAYLOAD_NCI ,NFC_DIRECTION_RX ); +if (!nci_plen (skb->data)) { +kfree_skb (skb); +break ; + } +/* Process frame */ switch (nci_mt (skb->data)) {case NCI_MT_RSP_PKT :
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 183/294 ixgbe: avoid sleeping allocation in ixgbe_ipsec_vf_add_sa()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Przemek Kitszel <[email protected]>
[ Upstream commit aec806fb4afba5fe80b09e29351379a4292baa43 ]
Change kzalloc() flags used in ixgbe_ipsec_vf_add_sa() to GFP_ATOMIC, to avoid sleeping in IRQ context.
Dan Carpenter, with the help of Smatch, has found following issue:
The patch eda0333ac293: "ixgbe: add VF IPsec management" from Aug 13, 2018 (linux-next), leads to the following Smatch static checker
warning: drivers/net/ethernet/intel/ixgbe/ixgbe_ipsec.c:917 ixgbe_ipsec_vf_add_sa()
warn: sleeping in IRQ context
The call tree that Smatch is worried about is:ixgbe_msix_other() <- IRQ handler
-> ixgbe_msg_task()
-> ixgbe_rcv_msg_from_vf()
-> ixgbe_ipsec_vf_add_sa()
--- drivers/net/ethernet/intel/ixgbe/ixgbe_ipsec.c | 16 ++++++++-------- 1 file changed, 8 insertions(+), 8 deletions(-)
drivers/net/ethernet/intel/ixgbe/ixgbe_ipsec.c +8 -8
@@ -909,7 +909,13 @@ int ixgbe_ipsec_vf_add_sa(struct ixgbe_adapter *adapter, u32 *msgbuf, u32 vf) goto err_out; } - xs =kzalloc (sizeof (*xs),GFP_KERNEL ); + algo =xfrm_aead_get_byname (aes_gcm_name,IXGBE_IPSEC_AUTH_BITS ,1 ); +if (unlikely (!algo)) { + err = -ENOENT ; + goto err_out; + } + + xs =kzalloc (sizeof (*xs),GFP_ATOMIC );if (unlikely (!xs)) { err = -ENOMEM ; goto err_out;
@@ -925,14 +931,8 @@ int ixgbe_ipsec_vf_add_sa(struct ixgbe_adapter *adapter, u32 *msgbuf, u32 vf)memcpy (&xs->id.daddr.a4, sam->addr,sizeof (xs->id.daddr.a4)); xs->xso.dev = adapter->netdev; - algo =xfrm_aead_get_byname (aes_gcm_name,IXGBE_IPSEC_AUTH_BITS ,1 ); -if (unlikely (!algo)) { - err = -ENOENT ; - goto err_xs; - } - aead_len =sizeof (*xs->aead) +IXGBE_IPSEC_KEY_BITS /8 ; - xs->aead =kzalloc (aead_len,GFP_KERNEL ); + xs->aead =kzalloc (aead_len,GFP_ATOMIC );if (unlikely (!xs->aead)) { err = -ENOMEM ; goto err_xs;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 184/294 tcp: properly terminate timers for kernel sockets
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Dumazet <[email protected]>
[ Upstream commit 151c9c724d05d5b0dd8acd3e11cb69ef1f2dbada ]
We had various syzbot reports about tcp timers firing after the corresponding netns has been dismantled.
Fortunately Josef Bacik could trigger the issue more often, and could test a patch I wrote two years ago.
When TCP sockets are closed, we call inet_csk_clear_xmit_timers() to 'stop' the timers.
inet_csk_clear_xmit_timers() can be called from any context, including when socket lock is held.
This is the reason it uses sk_stop_timer(), aka del_timer(). This means that ongoing timers might finish much later.
For user sockets, this is fine because each running timer holds a reference on the socket, and the user socket holds a reference on the netns.
For kernel sockets, we risk that the netns is freed before timer can complete, because kernel sockets do not hold reference on the netns.
This patch adds inet_csk_clear_xmit_timers_sync() function that using sk_stop_timer_sync() to make sure all timers are terminated before the kernel socket is released. Modules using kernel sockets close them in their netns exit() handler.
Also add sock_not_owned_by_me() helper to get LOCKDEP support : inet_csk_clear_xmit_timers_sync() must not be called while socket lock is held.
It is very possible we can revert in the future commit 3a58f13a881e ("net: rds: acquire refcount on TCP sockets") which attempted to solve the issue in rds only. (net/smc/af_smc.c and net/mptcp/subflow.c have similar code)
We probably can remove the check_net() tests from tcp_out_of_resources() and __tcp_close() in the future.
--- include/net/inet_connection_sock.h | 1 + include/net/sock.h | 7 +++++++ net/ipv4/inet_connection_sock.c | 14 ++++++++++++++ net/ipv4/tcp.c | 2 ++ 4 files changed, 24 insertions(+)
include/net/inet_connection_sock.h +1 -0
@@ -172,6 +172,7 @@ void inet_csk_init_xmit_timers(struct sock *sk,void (*delack_handler)(struct timer_list *), void (*keepalive_handler)(struct timer_list *));void inet_csk_clear_xmit_timers (struct sock *sk); +void inet_csk_clear_xmit_timers_sync (struct sock *sk);static inline void inet_csk_schedule_ack (struct sock *sk) {
include/net/sock.h +7 -0
@@ -1681,6 +1681,13 @@ static inline void sock_owned_by_me(const struct sock *sk)#endif } +static inline void sock_not_owned_by_me (const struct sock *sk) +{ +#ifdef CONFIG_LOCKDEP +WARN_ON_ONCE (lockdep_sock_is_held (sk) && debug_locks); +#endif +} +static inline bool sock_owned_by_user (const struct sock *sk) {sock_owned_by_me (sk);
net/ipv4/inet_connection_sock.c +14 -0
@@ -580,6 +580,20 @@ void inet_csk_clear_xmit_timers(struct sock *sk) }EXPORT_SYMBOL (inet_csk_clear_xmit_timers); +void inet_csk_clear_xmit_timers_sync (struct sock *sk) +{ +struct inet_connection_sock *icsk =inet_csk (sk); + +/* ongoing timer handlers need to acquire socket lock. */ +sock_not_owned_by_me (sk); + + icsk->icsk_pending = icsk->icsk_ack.pending =0 ; + +sk_stop_timer_sync (sk, &icsk->icsk_retransmit_timer); +sk_stop_timer_sync (sk, &icsk->icsk_delack_timer); +sk_stop_timer_sync (sk, &sk->sk_timer); +} +void inet_csk_delete_keepalive_timer (struct sock *sk) {sk_stop_timer (sk, &sk->sk_timer);
net/ipv4/tcp.c +2 -0
@@ -2717,6 +2717,8 @@ void tcp_close(struct sock *sk, long timeout)lock_sock (sk);__tcp_close (sk, timeout);release_sock (sk); +if (!sk->sk_net_refcnt) +inet_csk_clear_xmit_timers_sync (sk);sock_put (sk); }EXPORT_SYMBOL (tcp_close);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 185/294 ACPICA: debugger: check status of acpi_evaluate_object() in acpi_db_walk_for_fields()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Nikita Kiryushin <[email protected]>
[ Upstream commit 40e2710860e57411ab57a1529c5a2748abbe8a19 ]
ACPICA commit 9061cd9aa131205657c811a52a9f8325a040c6c9
Errors in acpi_evaluate_object() can lead to incorrect state of buffer.
This can lead to access to data in previously ACPI_FREEd buffer and secondary ACPI_FREE to the same buffer later.
Handle errors in acpi_evaluate_object the same way it is done earlier with acpi_ns_handle_to_pathname.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
--- drivers/acpi/acpica/dbnames.c | 8 ++++++-- 1 file changed, 6 insertions(+), 2 deletions(-)
drivers/acpi/acpica/dbnames.c +6 -2
@@ -550,8 +550,12 @@ acpi_db_walk_for_fields(acpi_handle obj_handle,ACPI_FREE (buffer.pointer); buffer.length =ACPI_ALLOCATE_LOCAL_BUFFER ; -acpi_evaluate_object (obj_handle,NULL ,NULL , &buffer); - + status =acpi_evaluate_object (obj_handle,NULL ,NULL , &buffer); +if (ACPI_FAILURE (status)) { +acpi_os_printf ("Could Not evaluate object %p\n" , + obj_handle); +return (AE_OK ); + }/* * Since this is a field unit, surround the output in braces */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 186/294 bpf: Protect against int overflow for stack access size
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Andrei Matei <[email protected]>
[ Upstream commit ecc6a2101840177e57c925c102d2d29f260d37c8 ]
This patch re-introduces protection against the size of access to stack memory being negative; the access size can appear negative as a result of overflowing its signed int representation. This should not actually happen, as there are other protections along the way, but we should protect against it anyway. One code path was missing such protections (fixed in the previous patch in the series), causing out-of-bounds array accesses in check_stack_range_initialized(). This patch causes the verification of a program with such a non-sensical access size to fail.
This check used to exist in a more indirect way, but was inadvertendly removed in a833a17aeac7.
--- kernel/bpf/verifier.c | 5 +++++ 1 file changed, 5 insertions(+)
kernel/bpf/verifier.c +5 -0
@@ -3941,6 +3941,11 @@ static int check_stack_access_within_bounds( err =check_stack_slot_within_bounds (min_off, state, type);if (!err && max_off >0 ) err = -EINVAL ;/* out of stack access into non-negative offsets */ +if (!err && access_size <0 ) +/* access_size should not be negative (or overflow an int); others checks +* along the way should have prevented such an access. +*/ + err = -EFAULT ;/* invalid negative access size; integer overflow? */ if (err) {if (tnum_is_const (reg->var_off)) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 187/294 Octeontx2-af: fix pause frame configuration in GMP mode
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hariprasad Kelam <[email protected]>
[ Upstream commit 40d4b4807cadd83fb3f46cc8cd67a945b5b25461 ]
The Octeontx2 MAC block (CGX) has separate data paths (SMU and GMP) for different speeds, allowing for efficient data transfer.
The previous patch which added pause frame configuration has a bug due to which pause frame feature is not working in GMP mode.
This patch fixes the issue by configurating appropriate registers.
--- drivers/net/ethernet/marvell/octeontx2/af/cgx.c | 5 +++++ 1 file changed, 5 insertions(+)
drivers/net/ethernet/marvell/octeontx2/af/cgx.c +5 -0
@@ -403,6 +403,11 @@ int cgx_lmac_set_pause_frm(void *cgxd, int lmac_id,if (!cgx || lmac_id >= cgx->lmac_count)return -ENODEV ; + cfg =cgx_read (cgx, lmac_id,CGXX_GMP_GMI_RXX_FRM_CTL ); + cfg &= ~CGX_GMP_GMI_RXX_FRM_CTL_CTL_BCK ; + cfg |= rx_pause ?CGX_GMP_GMI_RXX_FRM_CTL_CTL_BCK :0x0 ; +cgx_write (cgx, lmac_id,CGXX_GMP_GMI_RXX_FRM_CTL , cfg); + cfg =cgx_read (cgx, lmac_id,CGXX_SMUX_RX_FRM_CTL ); cfg &= ~CGX_SMUX_RX_FRM_CTL_CTL_BCK ; cfg |= rx_pause ?CGX_SMUX_RX_FRM_CTL_CTL_BCK :0x0 ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 188/294 dm integrity: fix out-of-range warning
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
[ Upstream commit 8e91c2342351e0f5ef6c0a704384a7f6fc70c3b2 ]
Depending on the value of CONFIG_HZ, clang complains about a pointless comparison:
drivers/md/dm-integrity.c:4085:12: error: result of comparison of
constant 42949672950 with expression of type 'unsigned int' is always false [-Werror,-Wtautological-constant-out-of-range-compare] if (val >= (uint64_t)UINT_MAX * 1000 / HZ) {
As the check remains useful for other configurations, shut up the warning by adding a second type cast to uint64_t.
--- drivers/md/dm-integrity.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/md/dm-integrity.c +1 -1
@@ -3937,7 +3937,7 @@ static int dm_integrity_ctr(struct dm_target *ti, unsigned argc, char **argv) }else if (sscanf (opt_string,"sectors_per_bit:%llu%c" , &llval, &dummy) ==1 ) { log2_sectors_per_bitmap_bit = !llval ?0 :__ilog2_u64 (llval); }else if (sscanf (opt_string,"bitmap_flush_interval:%u%c" , &val, &dummy) ==1 ) { -if (val >= (uint64_t )UINT_MAX *1000 /HZ ) { +if ((uint64_t )val >= (uint64_t )UINT_MAX *1000 /HZ ) { r = -EINVAL ; ti->error ="Invalid bitmap_flush_interval argument" ; goto bad;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 189/294 r8169: fix issue caused by buggy BIOS on certain boards with RTL8168d
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Heiner Kallweit <[email protected]>
commit 5d872c9f46bd2ea3524af3c2420a364a13667135 upstream.
On some boards with this chip version the BIOS is buggy and misses to reset the PHY page selector. This results in the PHY ID read accessing registers on a different page, returning a more or less random value. Fix this by resetting the page selector first.
--- drivers/net/ethernet/realtek/r8169_main.c | 9 +++++++++ 1 file changed, 9 insertions(+)
drivers/net/ethernet/realtek/r8169_main.c +9 -0
@@ -5181,6 +5181,15 @@ static int r8169_mdio_register(struct rtstruct mii_bus *new_bus;int ret; +/* On some boards with this chip version the BIOS is buggy and misses +* to reset the PHY page selector. This results in the PHY ID read +* accessing registers on a different page, returning a more or +* less random value. Fix this by resetting the page selector first. +*/ +if (tp->mac_version ==RTL_GIGA_MAC_VER_25 || + tp->mac_version ==RTL_GIGA_MAC_VER_26 ) +r8169_mdio_write (tp,0x1f ,0 ); + new_bus =devm_mdiobus_alloc (&pdev->dev);if (!new_bus)return -ENOMEM ;
Greg Kroah-Hartman
maintainerPATCH 190/294 x86/cpufeatures: Add new word for scattered features
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sandipan Das <[email protected]>
commit 7f274e609f3d5f45c22b1dd59053f6764458b492 upstream.
Add a new word for scattered features because all free bits among the existing Linux-defined auxiliary flags have been exhausted.
--- arch/x86/include/asm/cpufeature.h | 6 ++++-- arch/x86/include/asm/cpufeatures.h | 2 +- arch/x86/include/asm/disabled-features.h | 3 ++- arch/x86/include/asm/required-features.h | 3 ++- 4 files changed, 9 insertions(+), 5 deletions(-)
arch/x86/include/asm/cpufeature.h +4 -2
@@ -93,8 +93,9 @@ extern const char * const x86_bug_flags[ CHECK_BIT_IN_MASK_WORD(REQUIRED_MASK, 18, feature_bit) || \ CHECK_BIT_IN_MASK_WORD(REQUIRED_MASK, 19, feature_bit) || \ CHECK_BIT_IN_MASK_WORD(REQUIRED_MASK, 20, feature_bit) || \ + CHECK_BIT_IN_MASK_WORD(REQUIRED_MASK, 21, feature_bit) || \ REQUIRED_MASK_CHECK || \ - BUILD_BUG_ON_ZERO(NCAPINTS != 21)) + BUILD_BUG_ON_ZERO(NCAPINTS != 22))#define DISABLED_MASK_BIT_SET (feature_bit) \ ( CHECK_BIT_IN_MASK_WORD(DISABLED_MASK, 0, feature_bit) || \
@@ -118,8 +119,9 @@ extern const char * const x86_bug_flags[ CHECK_BIT_IN_MASK_WORD(DISABLED_MASK, 18, feature_bit) || \ CHECK_BIT_IN_MASK_WORD(DISABLED_MASK, 19, feature_bit) || \ CHECK_BIT_IN_MASK_WORD(DISABLED_MASK, 20, feature_bit) || \ + CHECK_BIT_IN_MASK_WORD(DISABLED_MASK, 21, feature_bit) || \ DISABLED_MASK_CHECK || \ - BUILD_BUG_ON_ZERO(NCAPINTS != 21)) + BUILD_BUG_ON_ZERO(NCAPINTS != 22))#define cpu_has (c, bit) \ (__builtin_constant_p(bit) && REQUIRED_MASK_BIT_SET(bit) ? 1 : \
arch/x86/include/asm/cpufeatures.h +1 -1
@@ -13,7 +13,7 @@/* * Defines x86 CPU feature bits */ -#define NCAPINTS 21/* N 32-bit words worth of info */ +#define NCAPINTS 22/* N 32-bit words worth of info */ #define NBUGINTS 2/* N 32-bit bug flags */ /*
arch/x86/include/asm/disabled-features.h +2 -1
@@ -103,6 +103,7 @@#define DISABLED_MASK18 0#define DISABLED_MASK19 0#define DISABLED_MASK20 0 -#define DISABLED_MASK_CHECK BUILD_BUG_ON_ZERO(NCAPINTS != 21) +#define DISABLED_MASK21 0 +#define DISABLED_MASK_CHECK BUILD_BUG_ON_ZERO(NCAPINTS != 22)#endif /* _ASM_X86_DISABLED_FEATURES_H */
arch/x86/include/asm/required-features.h +2 -1
@@ -103,6 +103,7 @@#define REQUIRED_MASK18 0#define REQUIRED_MASK19 0#define REQUIRED_MASK20 0 -#define REQUIRED_MASK_CHECK BUILD_BUG_ON_ZERO(NCAPINTS != 21) +#define REQUIRED_MASK21 0 +#define REQUIRED_MASK_CHECK BUILD_BUG_ON_ZERO(NCAPINTS != 22)#endif /* _ASM_X86_REQUIRED_FEATURES_H */
Greg Kroah-Hartman
maintainerPATCH 191/294 Bluetooth: hci_event: set the conn encrypted before conn establishes
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Hui Wang <[email protected]>
commit c569242cd49287d53b73a94233db40097d838535 upstream.
We have a BT headset (Lenovo Thinkplus XT99), the pairing and connecting has no problem, once this headset is paired, bluez will remember this device and will auto re-connect it whenever the device is powered on. The auto re-connecting works well with Windows and Android, but with Linux, it always fails. Through debugging, we found at the rfcomm connection stage, the bluetooth stack reports "Connection refused - security block (0x0003)".
For this device, the re-connecting negotiation process is different from other BT headsets, it sends the Link_KEY_REQUEST command before the CONNECT_REQUEST completes, and it doesn't send ENCRYPT_CHANGE command during the negotiation. When the device sends the "connect complete" to hci, the ev->encr_mode is 1.
So here in the conn_complete_evt(), if ev->encr_mode is 1, link type is ACL and HCI_CONN_ENCRYPT is not set, we set HCI_CONN_ENCRYPT to this conn, and update conn->enc_key_size accordingly.
After this change, this BT headset could re-connect with Linux successfully. This is the btmon log after applying the patch, after receiving the "Connect Complete" with "Encryption: Enabled", will send the command to read encryption key size:
Quoted 1 line
HCI Event: Connect Request (
0x04) plen 10
Address: 8C:3C:AA:D8:11:67 (OUI 8C-3C-AA)
Class: 0x240404
Major class: Audio/Video (headset, speaker, stereo, video, vcr) Minor class: Wearable Headset Device
Rendering (Printing, Speaker)
Audio (Speaker, Microphone, Headset)
Link type: ACL (0x01)
...
Quoted 1 line
HCI Event: Link Key Request (
0x17) plen 6
Address: 8C:3C:AA:D8:11:67 (OUI 8C-3C-AA)
< HCI Command: Link Key Request Reply (0x01|0x000b) plen 22
Address: 8C:3C:AA:D8:11:67 (OUI 8C-3C-AA)
Link key: ${32-hex-digits-key}...
Quoted 1 line
HCI Event: Connect Complete (
0x03) plen 11
Status: Success (0x00)
Handle: 256
Address: 8C:3C:AA:D8:11:67 (OUI 8C-3C-AA)
Link type: ACL (0x01)
Encryption: Enabled (0x01)
< HCI Command: Read Encryption Key... (0x05|0x0008) plen 2
Handle: 256
< ACL Data TX: Handle 256 flags 0x00 dlen 10
L2CAP: Information Request (0x0a) ident 1 len 2
Type: Extended features supported (0x0002)Quoted 1 line
HCI Event: Command Complete (
0x0e) plen 7
Read Encryption Key Size (0x05|0x0008) ncmd 1
Status: Success (0x00)
Handle: 256
Key size: 16--- net/bluetooth/hci_event.c | 25 +++++++++++++++++++++++++ 1 file changed, 25 insertions(+)
net/bluetooth/hci_event.c +25 -0
@@ -2636,6 +2636,31 @@ static void hci_conn_complete_evt(structif (test_bit (HCI_ENCRYPT , &hdev->flags))set_bit (HCI_CONN_ENCRYPT , &conn->flags); +/* "Link key request" completed ahead of "connect request" completes */ +if (ev->encr_mode ==1 && !test_bit (HCI_CONN_ENCRYPT , &conn->flags) && + ev->link_type ==ACL_LINK ) { +struct link_key *key; +struct hci_cp_read_enc_key_size cp; + + key =hci_find_link_key (hdev, &ev->bdaddr); +if (key) { +set_bit (HCI_CONN_ENCRYPT , &conn->flags); + +if (!(hdev->commands[20 ] &0x10 )) { + conn->enc_key_size =HCI_LINK_KEY_SIZE ; + }else { + cp.handle =cpu_to_le16 (conn->handle); +if (hci_send_cmd (hdev,HCI_OP_READ_ENC_KEY_SIZE , +sizeof (cp), &cp)) { +bt_dev_err (hdev,"sending read key size failed" ); + conn->enc_key_size =HCI_LINK_KEY_SIZE ; + } + } + +hci_encrypt_cfm (conn, ev->status); + } + } +/* Get remote features */ if (conn->type ==ACL_LINK ) {struct hci_cp_read_remote_features cp;
Greg Kroah-Hartman
maintainerPATCH 192/294 Bluetooth: Fix TOCTOU in HCI debugfs implementation
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bastien Nocera <[email protected]>
commit 7835fcfd132eb88b87e8eb901f88436f63ab60f7 upstream.
struct hci_dev members conn_info_max_age, conn_info_min_age, le_conn_max_interval, le_conn_min_interval, le_adv_max_interval, and le_adv_min_interval can be modified from the HCI core code, as well through debugfs.
The debugfs implementation, that's only available to privileged users, will check for boundaries, making sure that the minimum value being set is strictly above the maximum value that already exists, and vice-versa.
However, as both minimum and maximum values can be changed concurrently to us modifying them, we need to make sure that the value we check is the value we end up using.
For example, with ->conn_info_max_age set to 10, conn_info_min_age_set() gets called from vfs handlers to set conn_info_min_age to 8.
In conn_info_min_age_set(), this goes through:
if (val == 0 || val > hdev->conn_info_max_age) return -EINVAL;
Concurrently, conn_info_max_age_set() gets called to set to set the conn_info_max_age to 7:
if (val == 0 || val > hdev->conn_info_max_age) return -EINVAL;
That check will also pass because we used the old value (10) for conn_info_max_age.
After those checks that both passed, the struct hci_dev access is mutex-locked, disabling concurrent access, but that does not matter because the invalid value checks both passed, and we'll end up with conn_info_min_age = 8 and conn_info_max_age = 7
To fix this problem, we need to lock the structure access before so the check and assignment are not interrupted.
This fix was originally devised by the BassCheck[1] team, and considered the problem to be an atomicity one. This isn't the case as there aren't any concerns about the variable changing while we check it, but rather after we check it parallel to another change.
This patch fixes CVE-2024-24858 and CVE-2024-24857.
[1] https://sites.google.com/view/basscheck/
--- net/bluetooth/hci_debugfs.c | 48 +++++++++++++++++++++++++++++--------------- 1 file changed, 32 insertions(+), 16 deletions(-)
net/bluetooth/hci_debugfs.c +32 -16
@@ -216,10 +216,12 @@ static int conn_info_min_age_set(void *d {struct hci_dev *hdev = data; -if (val ==0 || val > hdev->conn_info_max_age) +hci_dev_lock (hdev); +if (val ==0 || val > hdev->conn_info_max_age) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->conn_info_min_age = val;hci_dev_unlock (hdev);
@@ -244,10 +246,12 @@ static int conn_info_max_age_set(void *d {struct hci_dev *hdev = data; -if (val ==0 || val < hdev->conn_info_min_age) +hci_dev_lock (hdev); +if (val ==0 || val < hdev->conn_info_min_age) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->conn_info_max_age = val;hci_dev_unlock (hdev);
@@ -526,10 +530,12 @@ static int sniff_min_interval_set(void * {struct hci_dev *hdev = data; -if (val ==0 || val %2 || val > hdev->sniff_max_interval) +hci_dev_lock (hdev); +if (val ==0 || val %2 || val > hdev->sniff_max_interval) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->sniff_min_interval = val;hci_dev_unlock (hdev);
@@ -554,10 +560,12 @@ static int sniff_max_interval_set(void * {struct hci_dev *hdev = data; -if (val ==0 || val %2 || val < hdev->sniff_min_interval) +hci_dev_lock (hdev); +if (val ==0 || val %2 || val < hdev->sniff_min_interval) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->sniff_max_interval = val;hci_dev_unlock (hdev);
@@ -798,10 +806,12 @@ static int conn_min_interval_set(void *d {struct hci_dev *hdev = data; -if (val <0x0006 || val >0x0c80 || val > hdev->le_conn_max_interval) +hci_dev_lock (hdev); +if (val <0x0006 || val >0x0c80 || val > hdev->le_conn_max_interval) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->le_conn_min_interval = val;hci_dev_unlock (hdev);
@@ -826,10 +836,12 @@ static int conn_max_interval_set(void *d {struct hci_dev *hdev = data; -if (val <0x0006 || val >0x0c80 || val < hdev->le_conn_min_interval) +hci_dev_lock (hdev); +if (val <0x0006 || val >0x0c80 || val < hdev->le_conn_min_interval) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->le_conn_max_interval = val;hci_dev_unlock (hdev);
@@ -938,10 +950,12 @@ static int adv_min_interval_set(void *da {struct hci_dev *hdev = data; -if (val <0x0020 || val >0x4000 || val > hdev->le_adv_max_interval) +hci_dev_lock (hdev); +if (val <0x0020 || val >0x4000 || val > hdev->le_adv_max_interval) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->le_adv_min_interval = val;hci_dev_unlock (hdev);
@@ -966,10 +980,12 @@ static int adv_max_interval_set(void *da {struct hci_dev *hdev = data; -if (val <0x0020 || val >0x4000 || val < hdev->le_adv_min_interval) +hci_dev_lock (hdev); +if (val <0x0020 || val >0x4000 || val < hdev->le_adv_min_interval) { +hci_dev_unlock (hdev);return -EINVAL ; + } -hci_dev_lock (hdev); hdev->le_adv_max_interval = val;hci_dev_unlock (hdev);
Greg Kroah-Hartman
maintainerPATCH 193/294 netfilter: nf_tables: disallow timeout for anonymous sets
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pablo Neira Ayuso <[email protected]>
commit e26d3009efda338f19016df4175f354a9bd0a4ab upstream.
Never used from userspace, disallow these parameters.
[Keerthana: code surrounding the patch is different because nft_set_desc is not present in v4.19-v5.10]
--- net/netfilter/nf_tables_api.c | 7 +++++++ 1 file changed, 7 insertions(+)
net/netfilter/nf_tables_api.c +7 -0
@@ -4457,6 +4457,9 @@ static int nf_tables_newset(struct net *if (!(flags &NFT_SET_TIMEOUT ))return -EINVAL ; +if (flags &NFT_SET_ANONYMOUS ) +return -EOPNOTSUPP ; + err =nf_msecs_to_jiffies64 (nla[NFTA_SET_TIMEOUT ], &timeout);if (err)return err;
@@ -4465,6 +4468,10 @@ static int nf_tables_newset(struct net *if (nla[NFTA_SET_GC_INTERVAL ] !=NULL ) {if (!(flags &NFT_SET_TIMEOUT ))return -EINVAL ; + +if (flags &NFT_SET_ANONYMOUS ) +return -EOPNOTSUPP ; + gc_int =ntohl (nla_get_be32 (nla[NFTA_SET_GC_INTERVAL ])); }
Greg Kroah-Hartman
maintainerPATCH 194/294 net/rds: fix possible cp null dereference
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Mahmoud Adam <[email protected]>
commit 62fc3357e079a07a22465b9b6ef71bb6ea75ee4b upstream.
cp might be null, calling cp->cp_conn would produce null dereference
[Simon Horman adds:]
Analysis:
* cp is a parameter of __rds_rdma_map and is not reassigned.
* The following call-sites pass a NULL cp argument to __rds_rdma_map()
- rds_get_mr()
- rds_get_mr_for_dest
* Prior to the code above, the following assumes that cp may be NULL (which is indicative, but could itself be unnecessary)
trans_private = rs->rs_transport->get_mr( sg, nents, rs, &mr->r_key, cp ? cp->cp_conn : NULL, args->vec.addr, args->vec.bytes, need_odp ? ODP_ZEROBASED : ODP_NOT_NEEDED);
* The code modified by this patch is guarded by IS_ERR(trans_private), where trans_private is assigned as per the previous point in this analysis.
The only implementation of get_mr that I could locate is rds_ib_get_mr() which can return an ERR_PTR if the conn (4th) argument is NULL.
* ret is set to PTR_ERR(trans_private).
rds_ib_get_mr can return ERR_PTR(-ENODEV) if the conn (4th) argument is NULL. Thus ret may be -ENODEV in which case the code in question will execute.
Conclusion:
* cp may be NULL at the point where this patch adds a check; this patch does seem to address a possible bug
--- net/rds/rdma.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
net/rds/rdma.c +1 -1
@@ -302,7 +302,7 @@ static int __rds_rdma_map(struct rds_soc } ret =PTR_ERR (trans_private);/* Trigger connection so that its ready for the next retry */ -if (ret == -ENODEV ) +if (ret == -ENODEV && cp)rds_conn_connect_if_down (cp->cp_conn); goto out; }
Greg Kroah-Hartman
maintainerPATCH 195/294 vfio/pci: Disable auto-enable of exclusive INTx IRQ
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Williamson <[email protected]>
[ Upstream commit fe9a7082684eb059b925c535682e68c34d487d43 ]
Currently for devices requiring masking at the irqchip for INTx, ie. devices without DisINTx support, the IRQ is enabled in request_irq() and subsequently disabled as necessary to align with the masked status flag. This presents a window where the interrupt could fire between these events, resulting in the IRQ incrementing the disable depth twice. This would be unrecoverable for a user since the masked flag prevents nested enables through vfio.
Instead, invert the logic using IRQF_NO_AUTOEN such that exclusive INTx is never auto-enabled, then unmask as required.
--- drivers/vfio/pci/vfio_pci_intrs.c | 17 ++++++++++------- 1 file changed, 10 insertions(+), 7 deletions(-)
drivers/vfio/pci/vfio_pci_intrs.c +10 -7
@@ -199,8 +199,15 @@ static int vfio_intx_set_signal(struct v vdev->ctx[0 ].trigger = trigger; +/* +* Devices without DisINTx support require an exclusive interrupt, +* IRQ masking is performed at the IRQ chip. The masked status is +* protected by vdev->irqlock. Setup the IRQ without auto-enable and +* unmask as necessary below under lock. DisINTx is unmodified by +* the IRQ configuration and may therefore use auto-enable. +*/ if (!vdev->pci_2_3) - irqflags =0 ; + irqflags =IRQF_NO_AUTOEN ; ret =request_irq (pdev->irq, vfio_intx_handler, irqflags, vdev->ctx[0 ].name, vdev);
@@ -211,13 +218,9 @@ static int vfio_intx_set_signal(struct vreturn ret; } -/* -* INTx disable will stick across the new irq setup, -* disable_irq won't. -*/ spin_lock_irqsave (&vdev->irqlock, flags); -if (!vdev->pci_2_3 && vdev->ctx[0 ].masked) -disable_irq_nosync (pdev->irq); +if (!vdev->pci_2_3 && !vdev->ctx[0 ].masked) +enable_irq (pdev->irq);spin_unlock_irqrestore (&vdev->irqlock, flags);return 0 ;
Greg Kroah-Hartman
maintainerPATCH 196/294 vfio/pci: Lock external INTx masking ops
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Williamson <[email protected]>
[ Upstream commit 810cd4bb53456d0503cc4e7934e063835152c1b7 ]
Mask operations through config space changes to DisINTx may race INTx configuration changes via ioctl. Create wrappers that add locking for paths outside of the core interrupt code.
In particular, irq_type is updated holding igate, therefore testing is_intx() requires holding igate. For example clearing DisINTx from config space can otherwise race changes of the interrupt configuration.
This aligns interfaces which may trigger the INTx eventfd into two camps, one side serialized by igate and the other only enabled while INTx is configured. A subsequent patch introduces synchronization for the latter flows.
--- drivers/vfio/pci/vfio_pci_intrs.c | 30 ++++++++++++++++++++++++------ 1 file changed, 24 insertions(+), 6 deletions(-)
drivers/vfio/pci/vfio_pci_intrs.c +24 -6
@@ -33,11 +33,13 @@ static void vfio_send_intx_eventfd(voideventfd_signal (vdev->ctx[0 ].trigger,1 ); } -void vfio_pci_intx_mask (struct vfio_pci_device *vdev) +static void __vfio_pci_intx_mask (struct vfio_pci_device *vdev) {struct pci_dev *pdev = vdev->pdev;unsigned long flags; +lockdep_assert_held (&vdev->igate); +spin_lock_irqsave (&vdev->irqlock, flags);/*
@@ -65,6 +67,13 @@ void vfio_pci_intx_mask(struct vfio_pci_spin_unlock_irqrestore (&vdev->irqlock, flags); } +void vfio_pci_intx_mask (struct vfio_pci_device *vdev) +{ +mutex_lock (&vdev->igate); +__vfio_pci_intx_mask (vdev); +mutex_unlock (&vdev->igate); +} +/* * If this is triggered by an eventfd, we can't call eventfd_signal * or else we'll deadlock on the eventfd wait queue. Return >0 when
@@ -107,12 +116,21 @@ static int vfio_pci_intx_unmask_handler(return ret; } -void vfio_pci_intx_unmask (struct vfio_pci_device *vdev) +static void __vfio_pci_intx_unmask (struct vfio_pci_device *vdev) { +lockdep_assert_held (&vdev->igate); +if (vfio_pci_intx_unmask_handler (vdev,NULL ) >0 )vfio_send_intx_eventfd (vdev,NULL ); } +void vfio_pci_intx_unmask (struct vfio_pci_device *vdev) +{ +mutex_lock (&vdev->igate); +__vfio_pci_intx_unmask (vdev); +mutex_unlock (&vdev->igate); +} +static irqreturn_t vfio_intx_handler (int irq,void *dev_id) {struct vfio_pci_device *vdev = dev_id;
@@ -428,11 +446,11 @@ static int vfio_pci_set_intx_unmask(strureturn -EINVAL ;if (flags &VFIO_IRQ_SET_DATA_NONE ) { -vfio_pci_intx_unmask (vdev); +__vfio_pci_intx_unmask (vdev); }else if (flags &VFIO_IRQ_SET_DATA_BOOL ) {uint8_t unmask = *(uint8_t *)data;if (unmask) -vfio_pci_intx_unmask (vdev); +__vfio_pci_intx_unmask (vdev); }else if (flags &VFIO_IRQ_SET_DATA_EVENTFD ) {int32_t fd = *(int32_t *)data;if (fd >=0 )
@@ -455,11 +473,11 @@ static int vfio_pci_set_intx_mask(structreturn -EINVAL ;if (flags &VFIO_IRQ_SET_DATA_NONE ) { -vfio_pci_intx_mask (vdev); +__vfio_pci_intx_mask (vdev); }else if (flags &VFIO_IRQ_SET_DATA_BOOL ) {uint8_t mask = *(uint8_t *)data;if (mask) -vfio_pci_intx_mask (vdev); +__vfio_pci_intx_mask (vdev); }else if (flags &VFIO_IRQ_SET_DATA_EVENTFD ) {return -ENOTTY ;/* XXX implement me */ }
Greg Kroah-Hartman
maintainerPATCH 197/294 vfio: Introduce interface to flush virqfd inject workqueue
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Williamson <[email protected]>
[ Upstream commit b620ecbd17a03cacd06f014a5d3f3a11285ce053 ]
In order to synchronize changes that can affect the thread callback, introduce an interface to force a flush of the inject workqueue. The irqfd pointer is only valid under spinlock, but the workqueue cannot be flushed under spinlock. Therefore the flush work for the irqfd is queued under spinlock. The vfio_irqfd_cleanup_wq workqueue is re-used for queuing this work such that flushing the workqueue is also ordered relative to shutdown.
--- drivers/vfio/virqfd.c | 21 +++++++++++++++++++++ include/linux/vfio.h | 2 ++ 2 files changed, 23 insertions(+)
drivers/vfio/virqfd.c +21 -0
@@ -101,6 +101,13 @@ static void virqfd_inject(struct work_st virqfd->thread (virqfd->opaque, virqfd->data); } +static void virqfd_flush_inject (struct work_struct *work) +{ + struct virqfd *virqfd = container_of(work, struct virqfd, flush_inject); + +flush_work (&virqfd->inject); +} + int vfio_virqfd_enable(void *opaque, int (*handler)(void *, void *), void (*thread)(void *, void *),
@@ -124,6 +131,7 @@ int vfio_virqfd_enable(void *opaque,INIT_WORK (&virqfd->shutdown, virqfd_shutdown);INIT_WORK (&virqfd->inject, virqfd_inject); +INIT_WORK (&virqfd->flush_inject, virqfd_flush_inject); irqfd =fdget (fd);if (!irqfd.file) {
@@ -214,6 +222,19 @@ void vfio_virqfd_disable(struct virqfd * }EXPORT_SYMBOL_GPL (vfio_virqfd_disable); +void vfio_virqfd_flush_thread (struct virqfd **pvirqfd) +{ +unsigned long flags; + +spin_lock_irqsave (&virqfd_lock, flags); +if (*pvirqfd && (*pvirqfd)->thread) +queue_work (vfio_irqfd_cleanup_wq, &(*pvirqfd)->flush_inject); +spin_unlock_irqrestore (&virqfd_lock, flags); + +flush_workqueue (vfio_irqfd_cleanup_wq); +} +EXPORT_SYMBOL_GPL (vfio_virqfd_flush_thread); +module_init (vfio_virqfd_init);module_exit (vfio_virqfd_exit);
include/linux/vfio.h +2 -0
@@ -221,6 +221,7 @@ struct virqfd {wait_queue_entry_t wait;poll_table pt;struct work_struct shutdown; +struct work_struct flush_inject;struct virqfd **pvirqfd; };
@@ -229,5 +230,6 @@ extern int vfio_virqfd_enable(void *opaqvoid (*thread)(void *,void *), void *data, struct virqfd **pvirqfd, int fd);extern void vfio_virqfd_disable (struct virqfd **pvirqfd); +void vfio_virqfd_flush_thread (struct virqfd **pvirqfd);#endif /* VFIO_H */
Greg Kroah-Hartman
maintainerPATCH 198/294 vfio/pci: Create persistent INTx handler
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Williamson <[email protected]>
[ Upstream commit 18c198c96a815c962adc2b9b77909eec0be7df4d ]
A vulnerability exists where the eventfd for INTx signaling can be deconfigured, which unregisters the IRQ handler but still allows eventfds to be signaled with a NULL context through the SET_IRQS ioctl or through unmask irqfd if the device interrupt is pending.
Ideally this could be solved with some additional locking; the igate mutex serializes the ioctl and config space accesses, and the interrupt handler is unregistered relative to the trigger, but the irqfd path runs asynchronous to those. The igate mutex cannot be acquired from the atomic context of the eventfd wake function. Disabling the irqfd relative to the eventfd registration is potentially incompatible with existing userspace.
As a result, the solution implemented here moves configuration of the INTx interrupt handler to track the lifetime of the INTx context object and irq_type configuration, rather than registration of a particular trigger eventfd. Synchronization is added between the ioctl path and eventfd_signal() wrapper such that the eventfd trigger can be dynamically updated relative to in-flight interrupts or irqfd callbacks.
--- drivers/vfio/pci/vfio_pci_intrs.c | 149 ++++++++++++++++++++------------------ 1 file changed, 82 insertions(+), 67 deletions(-)
drivers/vfio/pci/vfio_pci_intrs.c +82 -67
@@ -29,8 +29,13 @@ static void vfio_send_intx_eventfd(void {struct vfio_pci_device *vdev = opaque; -if (likely (is_intx (vdev) && !vdev->virq_disabled)) -eventfd_signal (vdev->ctx[0 ].trigger,1 ); +if (likely (is_intx (vdev) && !vdev->virq_disabled)) { +struct eventfd_ctx *trigger; + + trigger =READ_ONCE (vdev->ctx[0 ].trigger); +if (likely (trigger)) +eventfd_signal (trigger,1 ); + } }static void __vfio_pci_intx_mask (struct vfio_pci_device *vdev)
@@ -157,98 +162,104 @@ static irqreturn_t vfio_intx_handler(intreturn ret; } -static int vfio_intx_enable (struct vfio_pci_device *vdev) +static int vfio_intx_enable (struct vfio_pci_device *vdev, +struct eventfd_ctx *trigger) { +struct pci_dev *pdev = vdev->pdev; +unsigned long irqflags; +char *name; +int ret; +if (!is_irq_none (vdev))return -EINVAL ; -if (!vdev->pdev->irq) +if (!pdev->irq)return -ENODEV ; + name =kasprintf (GFP_KERNEL ,"vfio-intx(%s)" ,pci_name (pdev)); +if (!name) +return -ENOMEM ; + vdev->ctx =kzalloc (sizeof (struct vfio_pci_irq_ctx ),GFP_KERNEL );if (!vdev->ctx)return -ENOMEM ; vdev->num_ctx =1 ; + vdev->ctx[0 ].name = name; + vdev->ctx[0 ].trigger = trigger; +/* -* If the virtual interrupt is masked, restore it. Devices -* supporting DisINTx can be masked at the hardware level -* here, non-PCI-2.3 devices will have to wait until the -* interrupt is enabled. +* Fill the initial masked state based on virq_disabled. After +* enable, changing the DisINTx bit in vconfig directly changes INTx +* masking. igate prevents races during setup, once running masked +* is protected via irqlock. +* +* Devices supporting DisINTx also reflect the current mask state in +* the physical DisINTx bit, which is not affected during IRQ setup. +* +* Devices without DisINTx support require an exclusive interrupt. +* IRQ masking is performed at the IRQ chip. Again, igate protects +* against races during setup and IRQ handlers and irqfds are not +* yet active, therefore masked is stable and can be used to +* conditionally auto-enable the IRQ. +* +* irq_type must be stable while the IRQ handler is registered, +* therefore it must be set before request_irq(). */ vdev->ctx[0 ].masked = vdev->virq_disabled; -if (vdev->pci_2_3) -pci_intx (vdev->pdev, !vdev->ctx[0 ].masked); +if (vdev->pci_2_3) { +pci_intx (pdev, !vdev->ctx[0 ].masked); + irqflags =IRQF_SHARED ; + }else { + irqflags = vdev->ctx[0 ].masked ?IRQF_NO_AUTOEN :0 ; + } vdev->irq_type =VFIO_PCI_INTX_IRQ_INDEX ; + ret =request_irq (pdev->irq, vfio_intx_handler, + irqflags, vdev->ctx[0 ].name, vdev); +if (ret) { + vdev->irq_type =VFIO_PCI_NUM_IRQS ; +kfree (name); + vdev->num_ctx =0 ; +kfree (vdev->ctx); +return ret; + } +return 0 ; } -static int vfio_intx_set_signal (struct vfio_pci_device *vdev,int fd) +static int vfio_intx_set_signal (struct vfio_pci_device *vdev, +struct eventfd_ctx *trigger) {struct pci_dev *pdev = vdev->pdev; -unsigned long irqflags =IRQF_SHARED ; -struct eventfd_ctx *trigger; -unsigned long flags; -int ret; - -if (vdev->ctx[0 ].trigger) { -free_irq (pdev->irq, vdev); -kfree (vdev->ctx[0 ].name); -eventfd_ctx_put (vdev->ctx[0 ].trigger); - vdev->ctx[0 ].trigger =NULL ; - } - -if (fd <0 )/* Disable only */ -return 0 ; - - vdev->ctx[0 ].name =kasprintf (GFP_KERNEL ,"vfio-intx(%s)" , -pci_name (pdev)); -if (!vdev->ctx[0 ].name) -return -ENOMEM ; - - trigger =eventfd_ctx_fdget (fd); -if (IS_ERR (trigger)) { -kfree (vdev->ctx[0 ].name); -return PTR_ERR (trigger); - } +struct eventfd_ctx *old; - vdev->ctx[0 ].trigger = trigger; + old = vdev->ctx[0 ].trigger; -/* -* Devices without DisINTx support require an exclusive interrupt, -* IRQ masking is performed at the IRQ chip. The masked status is -* protected by vdev->irqlock. Setup the IRQ without auto-enable and -* unmask as necessary below under lock. DisINTx is unmodified by -* the IRQ configuration and may therefore use auto-enable. -*/ -if (!vdev->pci_2_3) - irqflags =IRQF_NO_AUTOEN ; +WRITE_ONCE (vdev->ctx[0 ].trigger, trigger); - ret =request_irq (pdev->irq, vfio_intx_handler, - irqflags, vdev->ctx[0 ].name, vdev); -if (ret) { - vdev->ctx[0 ].trigger =NULL ; -kfree (vdev->ctx[0 ].name); -eventfd_ctx_put (trigger); -return ret; +/* Releasing an old ctx requires synchronizing in-flight users */ +if (old) { +synchronize_irq (pdev->irq); +vfio_virqfd_flush_thread (&vdev->ctx[0 ].unmask); +eventfd_ctx_put (old); } -spin_lock_irqsave (&vdev->irqlock, flags); -if (!vdev->pci_2_3 && !vdev->ctx[0 ].masked) -enable_irq (pdev->irq); -spin_unlock_irqrestore (&vdev->irqlock, flags); -return 0 ; }static void vfio_intx_disable (struct vfio_pci_device *vdev) { +struct pci_dev *pdev = vdev->pdev; +vfio_virqfd_disable (&vdev->ctx[0 ].unmask);vfio_virqfd_disable (&vdev->ctx[0 ].mask); -vfio_intx_set_signal (vdev,-1 ); +free_irq (pdev->irq, vdev); +if (vdev->ctx[0 ].trigger) +eventfd_ctx_put (vdev->ctx[0 ].trigger); +kfree (vdev->ctx[0 ].name); vdev->irq_type =VFIO_PCI_NUM_IRQS ; vdev->num_ctx =0 ;kfree (vdev->ctx);
@@ -498,19 +509,23 @@ static int vfio_pci_set_intx_trigger(strreturn -EINVAL ;if (flags &VFIO_IRQ_SET_DATA_EVENTFD ) { +struct eventfd_ctx *trigger =NULL ;int32_t fd = *(int32_t *)data;int ret; +if (fd >=0 ) { + trigger =eventfd_ctx_fdget (fd); +if (IS_ERR (trigger)) +return PTR_ERR (trigger); + } +if (is_intx (vdev)) -return vfio_intx_set_signal (vdev, fd); + ret =vfio_intx_set_signal (vdev, trigger); +else + ret =vfio_intx_enable (vdev, trigger); - ret =vfio_intx_enable (vdev); -if (ret) -return ret; - - ret =vfio_intx_set_signal (vdev, fd); -if (ret) -vfio_intx_disable (vdev); +if (ret && trigger) +eventfd_ctx_put (trigger);return ret; }
Greg Kroah-Hartman
maintainerPATCH 199/294 vfio/platform: Create persistent IRQ handlers
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Williamson <[email protected]>
[ Upstream commit 675daf435e9f8e5a5eab140a9864dfad6668b375 ]
The vfio-platform SET_IRQS ioctl currently allows loopback triggering of an interrupt before a signaling eventfd has been configured by the user, which thereby allows a NULL pointer dereference.
Rather than register the IRQ relative to a valid trigger, register all IRQs in a disabled state in the device open path. This allows mask operations on the IRQ to nest within the overall enable state governed by a valid eventfd signal. This decouples @masked, protected by the @locked spinlock from @trigger, protected via the @igate mutex.
In doing so, it's guaranteed that changes to @trigger cannot race the IRQ handlers because the IRQ handler is synchronously disabled before modifying the trigger, and loopback triggering of the IRQ via ioctl is safe due to serialization with trigger changes via igate.
For compatibility, request_irq() failures are maintained to be local to the SET_IRQS ioctl rather than a fatal error in the open device path. This allows, for example, a userspace driver with polling mode support to continue to work regardless of moving the request_irq() call site. This necessarily blocks all SET_IRQS access to the failed index.
--- drivers/vfio/platform/vfio_platform_irq.c | 101 ++++++++++++++++++++---------- 1 file changed, 68 insertions(+), 33 deletions(-)
drivers/vfio/platform/vfio_platform_irq.c +68 -33
@@ -136,6 +136,16 @@ static int vfio_platform_set_irq_unmask(return 0 ; } +/* +* The trigger eventfd is guaranteed valid in the interrupt path +* and protected by the igate mutex when triggered via ioctl. +*/ +static void vfio_send_eventfd (struct vfio_platform_irq *irq_ctx) +{ +if (likely (irq_ctx->trigger)) +eventfd_signal (irq_ctx->trigger,1 ); +} +static irqreturn_t vfio_automasked_irq_handler (int irq,void *dev_id) {struct vfio_platform_irq *irq_ctx = dev_id;
@@ -155,7 +165,7 @@ static irqreturn_t vfio_automasked_irq_hspin_unlock_irqrestore (&irq_ctx->lock, flags);if (ret ==IRQ_HANDLED ) -eventfd_signal (irq_ctx->trigger,1 ); +vfio_send_eventfd (irq_ctx);return ret; }
@@ -164,22 +174,19 @@ static irqreturn_t vfio_irq_handler(int {struct vfio_platform_irq *irq_ctx = dev_id; -eventfd_signal (irq_ctx->trigger,1 ); +vfio_send_eventfd (irq_ctx);return IRQ_HANDLED ; }static int vfio_set_trigger (struct vfio_platform_device *vdev,int index, -int fd,irq_handler_t handler) +int fd) {struct vfio_platform_irq *irq = &vdev->irqs[index];struct eventfd_ctx *trigger; -int ret;if (irq->trigger) { -irq_clear_status_flags (irq->hwirq,IRQ_NOAUTOEN ); -free_irq (irq->hwirq, irq); -kfree (irq->name); +disable_irq (irq->hwirq);eventfd_ctx_put (irq->trigger); irq->trigger =NULL ; }
@@ -187,30 +194,20 @@ static int vfio_set_trigger(struct vfio_if (fd <0 )/* Disable only */ return 0 ; - irq->name =kasprintf (GFP_KERNEL ,"vfio-irq[%d](%s)" , - irq->hwirq, vdev->name); -if (!irq->name) -return -ENOMEM ; - trigger =eventfd_ctx_fdget (fd); -if (IS_ERR (trigger)) { -kfree (irq->name); +if (IS_ERR (trigger))return PTR_ERR (trigger); - } irq->trigger = trigger; -irq_set_status_flags (irq->hwirq,IRQ_NOAUTOEN ); - ret =request_irq (irq->hwirq, handler,0 , irq->name, irq); -if (ret) { -kfree (irq->name); -eventfd_ctx_put (trigger); - irq->trigger =NULL ; -return ret; - } - -if (!irq->masked) -enable_irq (irq->hwirq); +/* +* irq->masked effectively provides nested disables within the overall +* enable relative to trigger. Specifically request_irq() is called +* with NO_AUTOEN, therefore the IRQ is initially disabled. The user +* may only further disable the IRQ with a MASK operations because +* irq->masked is initially false. +*/ +enable_irq (irq->hwirq);return 0 ; }
@@ -229,7 +226,7 @@ static int vfio_platform_set_irq_trigger handler = vfio_irq_handler;if (!count && (flags &VFIO_IRQ_SET_DATA_NONE )) -return vfio_set_trigger (vdev, index,-1 , handler); +return vfio_set_trigger (vdev, index,-1 );if (start !=0 || count !=1 )return -EINVAL ;
@@ -237,7 +234,7 @@ static int vfio_platform_set_irq_triggerif (flags &VFIO_IRQ_SET_DATA_EVENTFD ) {int32_t fd = *(int32_t *)data; -return vfio_set_trigger (vdev, index, fd, handler); +return vfio_set_trigger (vdev, index, fd); }if (flags &VFIO_IRQ_SET_DATA_NONE ) {
@@ -261,6 +258,14 @@ int vfio_platform_set_irqs_ioctl(struct unsigned start, unsigned count, uint32_t flags, void *data) = NULL; +/* +* For compatibility, errors from request_irq() are local to the +* SET_IRQS path and reflected in the name pointer. This allows, +* for example, polling mode fallback for an exclusive IRQ failure. +*/ +if (IS_ERR (vdev->irqs[index].name)) +return PTR_ERR (vdev->irqs[index].name); +switch (flags &VFIO_IRQ_SET_ACTION_TYPE_MASK ) {case VFIO_IRQ_SET_ACTION_MASK : func = vfio_platform_set_irq_mask;
@@ -281,7 +286,7 @@ int vfio_platform_set_irqs_ioctl(structint vfio_platform_irq_init (struct vfio_platform_device *vdev) { -int cnt =0 , i; +int cnt =0 , i, ret =0 ;while (vdev->get_irq (vdev, cnt) >=0 ) cnt++;
@@ -292,29 +297,54 @@ int vfio_platform_irq_init(struct vfio_pfor (i =0 ; i < cnt; i++) {int hwirq = vdev->get_irq (vdev, i); +irq_handler_t handler = vfio_irq_handler; -if (hwirq <0 ) +if (hwirq <0 ) { + ret = -EINVAL ; goto err; + }spin_lock_init (&vdev->irqs[i].lock); vdev->irqs[i].flags =VFIO_IRQ_INFO_EVENTFD ; -if (irq_get_trigger_type (hwirq) &IRQ_TYPE_LEVEL_MASK ) +if (irq_get_trigger_type (hwirq) &IRQ_TYPE_LEVEL_MASK ) { vdev->irqs[i].flags |=VFIO_IRQ_INFO_MASKABLE |VFIO_IRQ_INFO_AUTOMASKED ; + handler = vfio_automasked_irq_handler; + } vdev->irqs[i].count =1 ; vdev->irqs[i].hwirq = hwirq; vdev->irqs[i].masked = false; + vdev->irqs[i].name =kasprintf (GFP_KERNEL , +"vfio-irq[%d](%s)" , hwirq, + vdev->name); +if (!vdev->irqs[i].name) { + ret = -ENOMEM ; + goto err; + } + + ret =request_irq (hwirq, handler,IRQF_NO_AUTOEN , + vdev->irqs[i].name, &vdev->irqs[i]); +if (ret) { +kfree (vdev->irqs[i].name); + vdev->irqs[i].name =ERR_PTR (ret); + } } vdev->num_irqs = cnt;return 0 ; err: +for (--i; i >=0 ; i--) { +if (!IS_ERR (vdev->irqs[i].name)) { +free_irq (vdev->irqs[i].hwirq, &vdev->irqs[i]); +kfree (vdev->irqs[i].name); + } + }kfree (vdev->irqs); -return -EINVAL ; +return ret; }void vfio_platform_irq_cleanup (struct vfio_platform_device *vdev)
@@ -324,7 +354,12 @@ void vfio_platform_irq_cleanup(struct vffor (i =0 ; i < vdev->num_irqs; i++) {vfio_virqfd_disable (&vdev->irqs[i].mask);vfio_virqfd_disable (&vdev->irqs[i].unmask); -vfio_set_trigger (vdev, i,-1 ,NULL ); +if (!IS_ERR (vdev->irqs[i].name)) { +free_irq (vdev->irqs[i].hwirq, &vdev->irqs[i]); +if (vdev->irqs[i].trigger) +eventfd_ctx_put (vdev->irqs[i].trigger); +kfree (vdev->irqs[i].name); + } } vdev->num_irqs =0 ;
Greg Kroah-Hartman
maintainerPATCH 200/294 vfio/fsl-mc: Block calling interrupt handler without trigger
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Williamson <[email protected]>
[ Upstream commit 7447d911af699a15f8d050dfcb7c680a86f87012 ]
The eventfd_ctx trigger pointer of the vfio_fsl_mc_irq object is initially NULL and may become NULL if the user sets the trigger eventfd to -1. The interrupt handler itself is guaranteed that trigger is always valid between request_irq() and free_irq(), but the loopback testing mechanisms to invoke the handler function need to test the trigger. The triggering and setting ioctl paths both make use of igate and are therefore mutually exclusive.
The vfio-fsl-mc driver does not make use of irqfds, nor does it support any sort of masking operations, therefore unlike vfio-pci and vfio-platform, the flow can remain essentially unchanged.
--- drivers/vfio/fsl-mc/vfio_fsl_mc_intr.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/vfio/fsl-mc/vfio_fsl_mc_intr.c +4 -3
@@ -142,13 +142,14 @@ static int vfio_fsl_mc_set_irq_trigger(s irq = &vdev->mc_irqs[index];if (flags &VFIO_IRQ_SET_DATA_NONE ) { -vfio_fsl_mc_irq_handler (hwirq, irq); +if (irq->trigger) +eventfd_signal (irq->trigger,1 ); }else if (flags &VFIO_IRQ_SET_DATA_BOOL ) {u8 trigger = *(u8 *)data; -if (trigger) -vfio_fsl_mc_irq_handler (hwirq, irq); +if (trigger && irq->trigger) +eventfd_signal (irq->trigger,1 ); }return 0 ;
Greg Kroah-Hartman
maintainerPATCH 201/294 io_uring: ensure 0 is returned on file registration success
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jens Axboe <[email protected]>
A previous backport mistakenly removed code that cleared 'ret' to zero, as the SCM logging was performed. Fix up the return value so we don't return an errant error on fixed file registration.
--- io_uring/io_uring.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
io_uring/io_uring.c +1 -1
@@ -8247,7 +8247,7 @@ static int io_sqe_files_register(struct }io_rsrc_node_switch (ctx,NULL ); -return ret; +return 0 ; out_fput:for (i =0 ; i < ctx->nr_user_files; i++) { file =io_file_from_index (ctx, i);
Greg Kroah-Hartman
maintainerPATCH 202/294 Revert "x86/mm/ident_map: Use gbpages only where full GB page should be mapped."
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ingo Molnar <[email protected]>
commit c567f2948f57bdc03ed03403ae0234085f376b7d upstream.
This reverts commit d794734c9bbfe22f86686dc2909c25f5ffe1a572.
While the original change tries to fix a bug, it also unintentionally broke existing systems, see the regressions reported at:
https://lore.kernel.org/all/[email protected]/
Since d794734c9bbf was also marked for -stable, let's back it out before causing more damage.
Note that due to another upstream change the revert was not 100% automatic:
0a845e0f6348 mm/treewide: replace pud_large() with pud_leaf()
--- arch/x86/mm/ident_map.c | 23 +++++------------------ 1 file changed, 5 insertions(+), 18 deletions(-)
arch/x86/mm/ident_map.c +5 -18
@@ -26,31 +26,18 @@ static int ident_pud_init(struct x86_mapfor (; addr < end; addr = next) {pud_t *pud = pud_page +pud_index (addr);pmd_t *pmd; -bool use_gbpage; next = (addr &PUD_MASK ) +PUD_SIZE ;if (next > end) next = end; -/* if this is already a gbpage, this portion is already mapped */ -if (pud_large (*pud)) -continue ; - -/* Is using a gbpage allowed? */ - use_gbpage = info->direct_gbpages; - -/* Don't use gbpage if it maps more than the requested region. */ -/* at the begining: */ - use_gbpage &= ((addr & ~PUD_MASK ) ==0 ); -/* ... or at the end: */ - use_gbpage &= ((next & ~PUD_MASK ) ==0 ); - -/* Never overwrite existing mappings */ - use_gbpage &= !pud_present (*pud); - -if (use_gbpage) { +if (info->direct_gbpages) {pud_t pudval; +if (pud_present (*pud)) +continue ; + + addr &=PUD_MASK ; pudval =__pud ((addr - info->offset) | info->page_flag);set_pud (pud, pudval);continue ;
Greg Kroah-Hartman
maintainerPATCH 203/294 mm, vmscan: prevent infinite loop for costly GFP_NOIO | __GFP_RETRY_MAYFAIL allocations
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Vlastimil Babka <[email protected]>
commit 803de9000f334b771afacb6ff3e78622916668b0 upstream.
Sven reports an infinite loop in __alloc_pages_slowpath() for costly order __GFP_RETRY_MAYFAIL allocations that are also GFP_NOIO. Such combination can happen in a suspend/resume context where a GFP_KERNEL allocation can have __GFP_IO masked out via gfp_allowed_mask.
Quoting Sven:
1. try to do a "costly" allocation (order > PAGE_ALLOC_COSTLY_ORDER) with __GFP_RETRY_MAYFAIL set.
2. page alloc's __alloc_pages_slowpath tries to get a page from the freelist. This fails because there is nothing free of that costly order.
3. page alloc tries to reclaim by calling __alloc_pages_direct_reclaim, which bails out because a zone is ready to be compacted; it pretends to have made a single page of progress.
4. page alloc tries to compact, but this always bails out early because __GFP_IO is not set (it's not passed by the snd allocator, and even if it were, we are suspending so the __GFP_IO flag would be cleared anyway).
5. page alloc believes reclaim progress was made (because of the pretense in item 3) and so it checks whether it should retry compaction. The compaction retry logic thinks it should try again, because:
a) reclaim is needed because of the early bail-out in item 4
b) a zonelist is suitable for compaction
6. goto 2. indefinite stall.
(end quote)
The immediate root cause is confusing the COMPACT_SKIPPED returned from __alloc_pages_direct_compact() (step 4) due to lack of __GFP_IO to be indicating a lack of order-0 pages, and in step 5 evaluating that in should_compact_retry() as a reason to retry, before incrementing and limiting the number of retries. There are however other places that wrongly assume that compaction can happen while we lack __GFP_IO.
To fix this, introduce gfp_compaction_allowed() to abstract the __GFP_IO evaluation and switch the open-coded test in try_to_compact_pages() to use it.
Also use the new helper in:
- compaction_ready(), which will make reclaim not bail out in step 3, so there's at least one attempt to actually reclaim, even if chances are small for a costly order
- in_reclaim_compaction() which will make should_continue_reclaim() return false and we don't over-reclaim unnecessarily
- in __alloc_pages_slowpath() to set a local variable can_compact, which is then used to avoid retrying reclaim/compaction for costly allocations (step 5) if we can't compact and also to skip the early compaction attempt that we do in some cases
--- include/linux/gfp.h | 9 +++++++++ mm/compaction.c | 7 +------ mm/page_alloc.c | 10 ++++++---- mm/vmscan.c | 5 ++++- 4 files changed, 20 insertions(+), 11 deletions(-)
include/linux/gfp.h +9 -0
@@ -623,6 +623,15 @@ static inline bool pm_suspended_storage( }#endif /* CONFIG_PM_SLEEP */ +/* +* Check if the gfp flags allow compaction - GFP_NOIO is a really +* tricky context because the migration might require IO. +*/ +static inline bool gfp_compaction_allowed (gfp_t gfp_mask) +{ +return IS_ENABLED (CONFIG_COMPACTION ) && (gfp_mask & __GFP_IO); +} +#ifdef CONFIG_CONTIG_ALLOC /* The below functions must be run on a range from a single zone. */ extern int alloc_contig_range(unsigned long start, unsigned long end,
mm/compaction.c +1 -6
@@ -2466,16 +2466,11 @@ enum compact_result try_to_compact_pages unsigned int alloc_flags, const struct alloc_context *ac, enum compact_priority prio, struct page **capture) { - int may_perform_io = gfp_mask & __GFP_IO; struct zoneref *z;struct zone *zone;enum compact_result rc =COMPACT_SKIPPED ; -/* -* Check if the GFP flags allow compaction - GFP_NOIO is really -* tricky context because the migration might require IO -*/ -if (!may_perform_io) +if (!gfp_compaction_allowed (gfp_mask))return COMPACT_SKIPPED ;trace_mm_compaction_try_to_compact_pages (order, gfp_mask, prio);
mm/page_alloc.c +6 -4
@@ -4644,6 +4644,7 @@ __alloc_pages_slowpath(gfp_t gfp_mask, u struct alloc_context *ac) {bool can_direct_reclaim = gfp_mask & __GFP_DIRECT_RECLAIM; +bool can_compact =gfp_compaction_allowed (gfp_mask);const bool costly_order = order >PAGE_ALLOC_COSTLY_ORDER ;struct page *page =NULL ;unsigned int alloc_flags;
@@ -4709,7 +4710,7 @@ restart:* Don't try this for allocations that are allowed to ignore * watermarks, as the ALLOC_NO_WATERMARKS attempt didn't yet happen. */ -if (can_direct_reclaim && +if (can_direct_reclaim && can_compact && (costly_order || (order >0 && ac->migratetype !=MIGRATE_MOVABLE )) && !gfp_pfmemalloc_allowed (gfp_mask)) {
@@ -4806,9 +4807,10 @@ retry:/* * Do not retry costly high order allocations unless they are -* __GFP_RETRY_MAYFAIL +* __GFP_RETRY_MAYFAIL and we can compact */ -if (costly_order && !(gfp_mask & __GFP_RETRY_MAYFAIL)) +if (costly_order && (!can_compact || + !(gfp_mask & __GFP_RETRY_MAYFAIL))) goto nopage; if (should_reclaim_retry(gfp_mask, order, ac, alloc_flags,
@@ -4821,7 +4823,7 @@ retry:* implementation of the compaction depends on the sufficient amount * of free memory (see __compaction_suitable) */ -if (did_some_progress >0 && +if (did_some_progress >0 && can_compact &&should_compact_retry (ac, order, alloc_flags, compact_result, &compact_priority, &compaction_retries))
mm/vmscan.c +4 -1
@@ -2546,7 +2546,7 @@ static void shrink_lruvec(struct lruvec/* Use reclaim/compaction for costly allocs or under memory pressure */ static bool in_reclaim_compaction (struct scan_control *sc) { -if (IS_ENABLED (CONFIG_COMPACTION ) && sc->order && +if (gfp_compaction_allowed (sc->gfp_mask) && sc->order && (sc->order >PAGE_ALLOC_COSTLY_ORDER || sc->priority <DEF_PRIORITY -2 ))return true;
@@ -2873,6 +2873,9 @@ static inline bool compaction_ready(struunsigned long watermark;enum compact_result suitable; +if (!gfp_compaction_allowed (sc->gfp_mask)) +return false; + suitable =compaction_suitable (zone, sc->order,0 , sc->reclaim_idx);if (suitable ==COMPACT_SUCCESS )/* Allocation should succeed already. Don't reclaim. */
Greg Kroah-Hartman
maintainerPATCH 204/294 x86/srso: Add SRSO mitigation for Hygon processors
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pu Wen <[email protected]>
commit a5ef7d68cea1344cf524f04981c2b3f80bedbb0d upstream.
Add mitigation for the speculative return stack overflow vulnerability which exists on Hygon processors too.
--- arch/x86/kernel/cpu/common.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
arch/x86/kernel/cpu/common.c +1 -1
@@ -1177,7 +1177,7 @@ static const struct x86_cpu_id cpu_vuln_VULNBL_AMD (0x15 ,RETBLEED ),VULNBL_AMD (0x16 ,RETBLEED ),VULNBL_AMD (0x17 ,RETBLEED |SRSO ), -VULNBL_HYGON (0x18 ,RETBLEED ), +VULNBL_HYGON (0x18 ,RETBLEED |SRSO ), VULNBL_AMD(0x19, SRSO), {} };
Greg Kroah-Hartman
maintainerPATCH 205/294 block: add check that partition length needs to be aligned with block size
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Min Li <[email protected]>
commit 6f64f866aa1ae6975c95d805ed51d7e9433a0016 upstream.
Before calling add partition or resize partition, there is no check on whether the length is aligned with the logical block size. If the logical block size of the disk is larger than 512 bytes, then the partition size maybe not the multiple of the logical block size, and when the last sector is read, bio_truncate() will adjust the bio size, resulting in an IO error if the size of the read command is smaller than the logical block size.If integrity data is supported, this will also result in a null pointer dereference when calling bio_integrity_free.
--- block/ioctl.c | 11 +++++++---- 1 file changed, 7 insertions(+), 4 deletions(-)
block/ioctl.c +7 -4
@@ -17,7 +17,7 @@ static int blkpg_do_ioctl(struct block_d struct blkpg_partition __user *upart, int op) {struct blkpg_partition p; -long long start, length; +sector_t start, length;if (!capable (CAP_SYS_ADMIN ))return -EACCES ;
@@ -32,6 +32,12 @@ static int blkpg_do_ioctl(struct block_dif (op ==BLKPG_DEL_PARTITION )return bdev_del_partition (bdev, p.pno); +if (p.start <0 || p.length <=0 || p.start + p.length <0 ) +return -EINVAL ; +/* Check that the partition is aligned to the block size */ +if (!IS_ALIGNED (p.start | p.length,bdev_logical_block_size (bdev))) +return -EINVAL ; + start = p.start >>SECTOR_SHIFT ; length = p.length >>SECTOR_SHIFT ;
@@ -46,9 +52,6 @@ static int blkpg_do_ioctl(struct block_dswitch (op) {case BLKPG_ADD_PARTITION : -/* check if partition is aligned to blocksize */ -if (p.start & (bdev_logical_block_size (bdev) -1 )) -return -EINVAL ;return bdev_add_partition (bdev, p.pno, start, length);case BLKPG_RESIZE_PARTITION :return bdev_resize_partition (bdev, p.pno, start, length);
Greg Kroah-Hartman
maintainerPATCH 206/294 netfilter: nf_tables: reject new basechain after table flag update
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pablo Neira Ayuso <[email protected]>
commit 994209ddf4f430946f6247616b2e33d179243769 upstream.
When dormant flag is toggled, hooks are disabled in the commit phase by iterating over current chains in table (existing and new).
The following configuration allows for an inconsistent state:
add table x
add chain x y { type filter hook input priority 0; } add table x { flags dormant; }
add chain x w { type filter hook input priority 1; }
which triggers the following warning when trying to unregister chain w which is already unregistered.
[ 127.322252] WARNING: CPU: 7 PID: 1211 at net/netfilter/core.c:50 1 __nf_unregister_net_hook+0x21a/0x260 [...] [ 127.322519] Call Trace: [ 127.322521] <TASK> [ 127.322524] ? __warn+0x9f/0x1a0 [ 127.322531] ? __nf_unregister_net_hook+0x21a/0x260 [ 127.322537] ? report_bug+0x1b1/0x1e0 [ 127.322545] ? handle_bug+0x3c/0x70 [ 127.322552] ? exc_invalid_op+0x17/0x40 [ 127.322556] ? asm_exc_invalid_op+0x1a/0x20 [ 127.322563] ? kasan_save_free_info+0x3b/0x60 [ 127.322570] ? __nf_unregister_net_hook+0x6a/0x260 [ 127.322577] ? __nf_unregister_net_hook+0x21a/0x260 [ 127.322583] ? __nf_unregister_net_hook+0x6a/0x260 [ 127.322590] ? __nf_tables_unregister_hook+0x8a/0xe0 [nf_tables] [ 127.322655] nft_table_disable+0x75/0xf0 [nf_tables] [ 127.322717] nf_tables_commit+0x2571/0x2620 [nf_tables]
--- net/netfilter/nf_tables_api.c | 3 +++ 1 file changed, 3 insertions(+)
net/netfilter/nf_tables_api.c +3 -0
@@ -2225,6 +2225,9 @@ static int nf_tables_addchain(struct nftstruct nft_stats __percpu *stats =NULL ;struct nft_chain_hook hook; +if (table->flags & __NFT_TABLE_F_UPDATE) +return -EINVAL ; +if (flags &NFT_CHAIN_BINDING )return -EOPNOTSUPP ;
Greg Kroah-Hartman
maintainerPATCH 207/294 netfilter: nf_tables: flush pending destroy work before exit_net release
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pablo Neira Ayuso <[email protected]>
commit 24cea9677025e0de419989ecb692acd4bb34cac2 upstream.
Similar to 2c9f0293280e ("netfilter: nf_tables: flush pending destroy work before netlink notifier") to address a race between exit_net and the destroy workqueue.
The trace below shows an element to be released via destroy workqueue while exit_net path (triggered via module removal) has already released the set that is used in such transaction.
[ 1360.547789] BUG: KASAN: slab-use-after-free in nf_tables_trans_destroy_work+0x3f5/0x590 [nf_tables] [ 1360.547861] Read of size 8 at addr ffff888140500cc0 by task kworker/4:1/152465 [ 1360.547870] CPU: 4 PID: 152465 Comm: kworker/4:1 Not tainted 6.8.0+ #359 [ 1360.547882] Workqueue: events nf_tables_trans_destroy_work [nf_tables] [ 1360.547984] Call Trace: [ 1360.547991] <TASK> [ 1360.547998] dump_stack_lvl+0x53/0x70 [ 1360.548014] print_report+0xc4/0x610 [ 1360.548026] ? __virt_addr_valid+0xba/0x160 [ 1360.548040] ? __pfx__raw_spin_lock_irqsave+0x10/0x10 [ 1360.548054] ? nf_tables_trans_destroy_work+0x3f5/0x590 [nf_tables] [ 1360.548176] kasan_report+0xae/0xe0 [ 1360.548189] ? nf_tables_trans_destroy_work+0x3f5/0x590 [nf_tables] [ 1360.548312] nf_tables_trans_destroy_work+0x3f5/0x590 [nf_tables] [ 1360.548447] ? __pfx_nf_tables_trans_destroy_work+0x10/0x10 [nf_tables] [ 1360.548577] ? _raw_spin_unlock_irq+0x18/0x30 [ 1360.548591] process_one_work+0x2f1/0x670 [ 1360.548610] worker_thread+0x4d3/0x760 [ 1360.548627] ? __pfx_worker_thread+0x10/0x10 [ 1360.548640] kthread+0x16b/0x1b0 [ 1360.548653] ? __pfx_kthread+0x10/0x10 [ 1360.548665] ret_from_fork+0x2f/0x50 [ 1360.548679] ? __pfx_kthread+0x10/0x10 [ 1360.548690] ret_from_fork_asm+0x1a/0x30 [ 1360.548707] </TASK>
[ 1360.548719] Allocated by task 192061: [ 1360.548726] kasan_save_stack+0x20/0x40 [ 1360.548739] kasan_save_track+0x14/0x30 [ 1360.548750] __kasan_kmalloc+0x8f/0xa0 [ 1360.548760] __kmalloc_node+0x1f1/0x450 [ 1360.548771] nf_tables_newset+0x10c7/0x1b50 [nf_tables] [ 1360.548883] nfnetlink_rcv_batch+0xbc4/0xdc0 [nfnetlink] [ 1360.548909] nfnetlink_rcv+0x1a8/0x1e0 [nfnetlink] [ 1360.548927] netlink_unicast+0x367/0x4f0 [ 1360.548935] netlink_sendmsg+0x34b/0x610 [ 1360.548944] ____sys_sendmsg+0x4d4/0x510 [ 1360.548953] ___sys_sendmsg+0xc9/0x120 [ 1360.548961] __sys_sendmsg+0xbe/0x140 [ 1360.548971] do_syscall_64+0x55/0x120 [ 1360.548982] entry_SYSCALL_64_after_hwframe+0x55/0x5d
[ 1360.548994] Freed by task 192222: [ 1360.548999] kasan_save_stack+0x20/0x40 [ 1360.549009] kasan_save_track+0x14/0x30 [ 1360.549019] kasan_save_free_info+0x3b/0x60 [ 1360.549028] poison_slab_object+0x100/0x180 [ 1360.549036] __kasan_slab_free+0x14/0x30 [ 1360.549042] kfree+0xb6/0x260 [ 1360.549049] __nft_release_table+0x473/0x6a0 [nf_tables] [ 1360.549131] nf_tables_exit_net+0x170/0x240 [nf_tables] [ 1360.549221] ops_exit_list+0x50/0xa0 [ 1360.549229] free_exit_list+0x101/0x140 [ 1360.549236] unregister_pernet_operations+0x107/0x160 [ 1360.549245] unregister_pernet_subsys+0x1c/0x30 [ 1360.549254] nf_tables_module_exit+0x43/0x80 [nf_tables] [ 1360.549345] __do_sys_delete_module+0x253/0x370 [ 1360.549352] do_syscall_64+0x55/0x120 [ 1360.549360] entry_SYSCALL_64_after_hwframe+0x55/0x5d
(gdb) list *__nft_release_table+0x4730x1e033 is in __nft_release_table (net/netfilter/nf_tables_api.c:11354).
11349 list_for_each_entry_safe(flowtable, nf, &table->flowtables, list) {
11350 list_del(&flowtable->list);
11351 nft_use_dec(&table->use);
11352 nf_tables_flowtable_destroy(flowtable);
11353 }
11354 list_for_each_entry_safe(set, ns, &table->sets, list) {
11355 list_del(&set->list);
11356 nft_use_dec(&table->use);
11357 if (set->flags & (NFT_SET_MAP | NFT_SET_OBJECT))11358 nft_map_deactivate(&ctx, set);
(gdb)
[ 1360.549372] Last potentially related work creation: [ 1360.549376] kasan_save_stack+0x20/0x40 [ 1360.549384] __kasan_record_aux_stack+0x9b/0xb0 [ 1360.549392] __queue_work+0x3fb/0x780 [ 1360.549399] queue_work_on+0x4f/0x60 [ 1360.549407] nft_rhash_remove+0x33b/0x340 [nf_tables] [ 1360.549516] nf_tables_commit+0x1c6a/0x2620 [nf_tables] [ 1360.549625] nfnetlink_rcv_batch+0x728/0xdc0 [nfnetlink] [ 1360.549647] nfnetlink_rcv+0x1a8/0x1e0 [nfnetlink] [ 1360.549671] netlink_unicast+0x367/0x4f0 [ 1360.549680] netlink_sendmsg+0x34b/0x610 [ 1360.549690] ____sys_sendmsg+0x4d4/0x510 [ 1360.549697] ___sys_sendmsg+0xc9/0x120 [ 1360.549706] __sys_sendmsg+0xbe/0x140 [ 1360.549715] do_syscall_64+0x55/0x120 [ 1360.549725] entry_SYSCALL_64_after_hwframe+0x55/0x5d
--- net/netfilter/nf_tables_api.c | 1 + 1 file changed, 1 insertion(+)
net/netfilter/nf_tables_api.c +1 -0
@@ -9796,6 +9796,7 @@ static void __exit nf_tables_module_exitunregister_netdevice_notifier (&nf_tables_flowtable_notifier);nft_chain_filter_fini ();nft_chain_route_fini (); +nf_tables_trans_destroy_flush_work ();unregister_pernet_subsys (&nf_tables_net_ops);cancel_work_sync (&trans_gc_work);cancel_work_sync (&trans_destroy_work);
Greg Kroah-Hartman
maintainerPATCH 208/294 netfilter: nf_tables: Fix potential data-race in __nft_flowtable_type_get()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ziyang Xuan <[email protected]>
commit 24225011d81b471acc0e1e315b7d9905459a6304 upstream.
nft_unregister_flowtable_type() within nf_flow_inet_module_exit() can concurrent with __nft_flowtable_type_get() within nf_tables_newflowtable(). And thhere is not any protection when iterate over nf_tables_flowtables list in __nft_flowtable_type_get(). Therefore, there is pertential data-race of nf_tables_flowtables list entry.
Use list_for_each_entry_rcu() to iterate over nf_tables_flowtables list in __nft_flowtable_type_get(), and use rcu_read_lock() in the caller nft_flowtable_type_get() to protect the entire type query process.
--- net/netfilter/nf_tables_api.c | 9 +++++++-- 1 file changed, 7 insertions(+), 2 deletions(-)
net/netfilter/nf_tables_api.c +7 -2
@@ -6879,11 +6879,12 @@ static int nft_flowtable_parse_hook(consreturn err; } +/* call under rcu_read_lock */ static const struct nf_flowtable_type *__nft_flowtable_type_get (u8 family) {const struct nf_flowtable_type *type; -list_for_each_entry (type, &nf_tables_flowtables, list) { +list_for_each_entry_rcu (type, &nf_tables_flowtables, list) {if (family == type->family)return type; }
@@ -6895,9 +6896,13 @@ nft_flowtable_type_get(struct net *net, {const struct nf_flowtable_type *type; +rcu_read_lock (); type =__nft_flowtable_type_get (family); -if (type !=NULL &&try_module_get (type->owner)) +if (type !=NULL &&try_module_get (type->owner)) { +rcu_read_unlock ();return type; + } +rcu_read_unlock ();lockdep_nfnl_nft_mutex_not_held ();#ifdef CONFIG_MODULES
Greg Kroah-Hartman
maintainerPATCH 209/294 netfilter: validate user input for expected length
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Dumazet <[email protected]>
commit 0c83842df40f86e529db6842231154772c20edcc upstream.
I got multiple syzbot reports showing old bugs exposed by BPF after commit 20f2505fb436 ("bpf: Try to avoid kzalloc in cgroup/{s,g}etsockopt")
setsockopt() @optlen argument should be taken into account before copying data.
BUG: KASAN: slab-out-of-bounds in copy_from_sockptr_offset include/linux/sockptr.h:49 [inline] BUG: KASAN: slab-out-of-bounds in copy_from_sockptr include/linux/sockptr.h:55 [inline] BUG: KASAN: slab-out-of-bounds in do_replace net/ipv4/netfilter/ip_tables.c:1111 [inline] BUG: KASAN: slab-out-of-bounds in do_ipt_set_ctl+0x902/0x3dd0 net/ipv4/netfilter/ip_tables.c:1627 Read of size 96 at addr ffff88802cd73da0 by task syz-executor.4/7238 CPU: 1 PID: 7238 Comm: syz-executor.4 Not tainted 6.9.0-rc2-next-20240403-syzkaller #0 Hardware name: Google Google Compute Engine/Google Compute Engine, BIOS Google 03/27/2024 Call Trace: <TASK> __dump_stack lib/dump_stack.c:88 [inline] dump_stack_lvl+0x241/0x360 lib/dump_stack.c:114 print_address_description mm/kasan/report.c:377 [inline] print_report+0x169/0x550 mm/kasan/report.c:488 kasan_report+0x143/0x180 mm/kasan/report.c:601 kasan_check_range+0x282/0x290 mm/kasan/generic.c:189 __asan_memcpy+0x29/0x70 mm/kasan/shadow.c:105 copy_from_sockptr_offset include/linux/sockptr.h:49 [inline] copy_from_sockptr include/linux/sockptr.h:55 [inline] do_replace net/ipv4/netfilter/ip_tables.c:1111 [inline] do_ipt_set_ctl+0x902/0x3dd0 net/ipv4/netfilter/ip_tables.c:1627 nf_setsockopt+0x295/0x2c0 net/netfilter/nf_sockopt.c:101 do_sock_setsockopt+0x3af/0x720 net/socket.c:2311 __sys_setsockopt+0x1ae/0x250 net/socket.c:2334 __do_sys_setsockopt net/socket.c:2343 [inline] __se_sys_setsockopt net/socket.c:2340 [inline] __x64_sys_setsockopt+0xb5/0xd0 net/socket.c:2340 do_syscall_64+0xfb/0x240 entry_SYSCALL_64_after_hwframe+0x72/0x7a RIP: 0033:0x7fd22067dde9 Code: 28 00 00 00 75 05 48 83 c4 28 c3 e8 e1 20 00 00 90 48 89 f8 48 89 f7 48 89 d6 48 89 ca 4d 89 c2 4d 89 c8 4c 8b 4c 24 08 0f 05 <48> 3d 01 f0 ff ff 73 01 c3 48 c7 c1 b0 ff ff ff f7 d8 64 89 01 48 RSP: 002b:00007fd21f9ff0c8 EFLAGS: 00000246 ORIG_RAX: 0000000000000036 RAX: ffffffffffffffda RBX: 00007fd2207abf80 RCX: 00007fd22067dde9 RDX: 0000000000000040 RSI: 0000000000000000 RDI: 0000000000000003 RBP: 00007fd2206ca47a R08: 0000000000000001 R09: 0000000000000000 R10: 0000000020000880 R11: 0000000000000246 R12: 0000000000000000 R13: 000000000000000b R14: 00007fd2207abf80 R15: 00007ffd2d0170d8 </TASK> Allocated by task 7238: kasan_save_stack mm/kasan/common.c:47 [inline] kasan_save_track+0x3f/0x80 mm/kasan/common.c:68 poison_kmalloc_redzone mm/kasan/common.c:370 [inline] __kasan_kmalloc+0x98/0xb0 mm/kasan/common.c:387 kasan_kmalloc include/linux/kasan.h:211 [inline] __do_kmalloc_node mm/slub.c:4069 [inline] __kmalloc_noprof+0x200/0x410 mm/slub.c:4082 kmalloc_noprof include/linux/slab.h:664 [inline] __cgroup_bpf_run_filter_setsockopt+0xd47/0x1050 kernel/bpf/cgroup.c:1869 do_sock_setsockopt+0x6b4/0x720 net/socket.c:2293 __sys_setsockopt+0x1ae/0x250 net/socket.c:2334 __do_sys_setsockopt net/socket.c:2343 [inline] __se_sys_setsockopt net/socket.c:2340 [inline] __x64_sys_setsockopt+0xb5/0xd0 net/socket.c:2340 do_syscall_64+0xfb/0x240 entry_SYSCALL_64_after_hwframe+0x72/0x7a The buggy address belongs to the object at ffff88802cd73da0 which belongs to the cache kmalloc-8 of size 8
The buggy address is located 0 bytes inside of
allocated 1-byte region [ffff88802cd73da0, ffff88802cd73da1)
The buggy address belongs to the physical page:
page: refcount:1 mapcount:0 mapping:0000000000000000 index:0xffff88802cd73020 pfn:0x2cd73
flags: 0xfff80000000000(node=0|zone=1|lastcpupid=0xfff)
page_type: 0xffffefff(slab)
raw: 00fff80000000000 ffff888015041280 dead000000000100 dead000000000122
raw: ffff88802cd73020 000000008080007f 00000001ffffefff 0000000000000000
page dumped because: kasan: bad access detected
page_owner tracks the page as allocated
page last allocated via order 0, migratetype Unmovable, gfp_mask 0x12cc0(GFP_KERNEL|__GFP_NOWARN|__GFP_NORETRY), pid 5103, tgid 2119833701 (syz-executor.4), ts 5103, free_ts 70804600828
set_page_owner include/linux/page_owner.h:32 [inline]
post_alloc_hook+0x1f3/0x230 mm/page_alloc.c:1490
prep_new_page mm/page_alloc.c:1498 [inline]
get_page_from_freelist+0x2e7e/0x2f40 mm/page_alloc.c:3454
__alloc_pages_noprof+0x256/0x6c0 mm/page_alloc.c:4712
__alloc_pages_node_noprof include/linux/gfp.h:244 [inline]
alloc_pages_node_noprof include/linux/gfp.h:271 [inline]
alloc_slab_page+0x5f/0x120 mm/slub.c:2249
allocate_slab+0x5a/0x2e0 mm/slub.c:2412
new_slab mm/slub.c:2465 [inline]
___slab_alloc+0xcd1/0x14b0 mm/slub.c:3615
__slab_alloc+0x58/0xa0 mm/slub.c:3705
__slab_alloc_node mm/slub.c:3758 [inline]
slab_alloc_node mm/slub.c:3936 [inline]
__do_kmalloc_node mm/slub.c:4068 [inline]
kmalloc_node_track_caller_noprof+0x286/0x450 mm/slub.c:4089
kstrdup+0x3a/0x80 mm/util.c:62
device_rename+0xb5/0x1b0 drivers/base/core.c:4558
dev_change_name+0x275/0x860 net/core/dev.c:1232
do_setlink+0xa4b/0x41f0 net/core/rtnetlink.c:2864
__rtnl_newlink net/core/rtnetlink.c:3680 [inline]
rtnl_newlink+0x180b/0x20a0 net/core/rtnetlink.c:3727
rtnetlink_rcv_msg+0x89b/0x10d0 net/core/rtnetlink.c:6594
netlink_rcv_skb+0x1e3/0x430 net/netlink/af_netlink.c:2559
netlink_unicast_kernel net/netlink/af_netlink.c:1335 [inline]
netlink_unicast+0x7ea/0x980 net/netlink/af_netlink.c:1361
page last free pid 5146 tgid 5146 stack trace:
reset_page_owner include/linux/page_owner.h:25 [inline]
free_pages_prepare mm/page_alloc.c:1110 [inline]
free_unref_page+0xd3c/0xec0 mm/page_alloc.c:2617
discard_slab mm/slub.c:2511 [inline]
__put_partials+0xeb/0x130 mm/slub.c:2980
put_cpu_partial+0x17c/0x250 mm/slub.c:3055
__slab_free+0x2ea/0x3d0 mm/slub.c:4254
qlink_free mm/kasan/quarantine.c:163 [inline]
qlist_free_all+0x9e/0x140 mm/kasan/quarantine.c:179
kasan_quarantine_reduce+0x14f/0x170 mm/kasan/quarantine.c:286
__kasan_slab_alloc+0x23/0x80 mm/kasan/common.c:322
kasan_slab_alloc include/linux/kasan.h:201 [inline]
slab_post_alloc_hook mm/slub.c:3888 [inline]
slab_alloc_node mm/slub.c:3948 [inline]
__do_kmalloc_node mm/slub.c:4068 [inline]
__kmalloc_node_noprof+0x1d7/0x450 mm/slub.c:4076
kmalloc_node_noprof include/linux/slab.h:681 [inline]
kvmalloc_node_noprof+0x72/0x190 mm/util.c:634
bucket_table_alloc lib/rhashtable.c:186 [inline]
rhashtable_rehash_alloc+0x9e/0x290 lib/rhashtable.c:367
rht_deferred_worker+0x4e1/0x2440 lib/rhashtable.c:427
process_one_work kernel/workqueue.c:3218 [inline]
process_scheduled_works+0xa2c/0x1830 kernel/workqueue.c:3299
worker_thread+0x86d/0xd70 kernel/workqueue.c:3380
kthread+0x2f0/0x390 kernel/kthread.c:388
ret_from_fork+0x4b/0x80 arch/x86/kernel/process.c:147
ret_from_fork_asm+0x1a/0x30 arch/x86/entry/entry_64.S:243
Memory state around the buggy address:
ffff88802cd73c80: 07 fc fc fc 05 fc fc fc 05 fc fc fc fa fc fc fc
ffff88802cd73d00: fa fc fc fc fa fc fc fc fa fc fc fc fa fc fc fc
>ffff88802cd73d80: fa fc fc fc 01 fc fc fc fa fc fc fc fa fc fc fc
^
ffff88802cd73e00: fa fc fc fc fa fc fc fc 05 fc fc fc 07 fc fc fc
ffff88802cd73e80: 07 fc fc fc 07 fc fc fc 07 fc fc fc 07 fc fc fc--- net/bridge/netfilter/ebtables.c | 6 ++++++ net/ipv4/netfilter/arp_tables.c | 4 ++++ net/ipv4/netfilter/ip_tables.c | 4 ++++ net/ipv6/netfilter/ip6_tables.c | 4 ++++ 4 files changed, 18 insertions(+)
net/bridge/netfilter/ebtables.c +6 -0
@@ -1070,6 +1070,8 @@ static int do_replace(struct net *net, sstruct ebt_table_info *newinfo;struct ebt_replace tmp; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
@@ -1309,6 +1311,8 @@ static int update_counters(struct net *n {struct ebt_replace hlp; +if (len <sizeof (hlp)) +return -EINVAL ;if (copy_from_sockptr (&hlp, arg,sizeof (hlp)))return -EFAULT ;
@@ -2238,6 +2242,8 @@ static int compat_update_counters(struct {struct compat_ebt_replace hlp; +if (len <sizeof (hlp)) +return -EINVAL ;if (copy_from_sockptr (&hlp, arg,sizeof (hlp)))return -EFAULT ;
net/ipv4/netfilter/arp_tables.c +4 -0
@@ -955,6 +955,8 @@ static int do_replace(struct net *net, svoid *loc_cpu_entry;struct arpt_entry *iter; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
@@ -1253,6 +1255,8 @@ static int compat_do_replace(struct netvoid *loc_cpu_entry;struct arpt_entry *iter; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
net/ipv4/netfilter/ip_tables.c +4 -0
@@ -1109,6 +1109,8 @@ do_replace(struct net *net, sockptr_t arvoid *loc_cpu_entry;struct ipt_entry *iter; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
@@ -1493,6 +1495,8 @@ compat_do_replace(struct net *net, sockpvoid *loc_cpu_entry;struct ipt_entry *iter; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
net/ipv6/netfilter/ip6_tables.c +4 -0
@@ -1127,6 +1127,8 @@ do_replace(struct net *net, sockptr_t arvoid *loc_cpu_entry;struct ip6t_entry *iter; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
@@ -1503,6 +1505,8 @@ compat_do_replace(struct net *net, sockpvoid *loc_cpu_entry;struct ip6t_entry *iter; +if (len <sizeof (tmp)) +return -EINVAL ;if (copy_from_sockptr (&tmp, arg,sizeof (tmp)) !=0 )return -EFAULT ;
Greg Kroah-Hartman
maintainerPATCH 210/294 vboxsf: Avoid an spurious warning if load_nls_xxx() fails
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Christophe JAILLET <[email protected]>
commit de3f64b738af57e2732b91a0774facc675b75b54 upstream.
If an load_nls_xxx() function fails a few lines above, the 'sbi->bdi_id' is still 0.
So, in the error handling path, we will call ida_simple_remove(..., 0) which is not allocated yet.
In order to prevent a spurious "ida_free called for id=0 which is not allocated." message, tweak the error handling path and add a new label.
--- fs/vboxsf/super.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
fs/vboxsf/super.c +2 -1
@@ -151,7 +151,7 @@ static int vboxsf_fill_super(struct supeif (!sbi->nls) {vbg_err ("vboxsf: Count not load '%s' nls\n" , nls_name); err = -EINVAL ; - goto fail_free; + goto fail_destroy_idr; } }
@@ -224,6 +224,7 @@ fail_free:ida_simple_remove (&vboxsf_bdi_ida, sbi->bdi_id);if (sbi->nls)unload_nls (sbi->nls); +fail_destroy_idr:idr_destroy (&sbi->ino_idr);kfree (sbi);return err;
Greg Kroah-Hartman
maintainerPATCH 211/294 bpf, sockmap: Prevent lock inversion deadlock in map delete elem
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jakub Sitnicki <[email protected]>
commit ff91059932401894e6c86341915615c5eb0eca48 upstream.
syzkaller started using corpuses where a BPF tracing program deletes elements from a sockmap/sockhash map. Because BPF tracing programs can be invoked from any interrupt context, locks taken during a map_delete_elem operation must be hardirq-safe. Otherwise a deadlock due to lock inversion is possible, as reported by lockdep:
CPU0 CPU1
---- ----
lock(&htab->buckets[i].lock);
local_irq_disable();
lock(&host->lock);
lock(&htab->buckets[i].lock);
<Interrupt>
lock(&host->lock);Locks in sockmap are hardirq-unsafe by design. We expects elements to be deleted from sockmap/sockhash only in task (normal) context with interrupts enabled, or in softirq context.
Detect when map_delete_elem operation is invoked from a context which is _not_ hardirq-unsafe, that is interrupts are disabled, and bail out with an error.
Note that map updates are not affected by this issue. BPF verifier does not allow updating sockmap/sockhash from a BPF tracing program today.
--- net/core/sock_map.c | 6 ++++++ 1 file changed, 6 insertions(+)
net/core/sock_map.c +6 -0
@@ -422,6 +422,9 @@ static int __sock_map_delete(struct bpf_struct sock *sk;int err =0 ; +if (irqs_disabled ()) +return -EOPNOTSUPP ;/* locks here are hardirq-unsafe */ +raw_spin_lock_bh (&stab->lock); sk = *psk;if (!sk_test || sk_test == sk)
@@ -955,6 +958,9 @@ static int sock_hash_delete_elem(structstruct bpf_shtab_elem *elem;int ret = -ENOENT ; +if (irqs_disabled ()) +return -EOPNOTSUPP ;/* locks here are hardirq-unsafe */ + hash =sock_hash_bucket_hash (key, key_size); bucket =sock_hash_select_bucket (htab, hash);
Greg Kroah-Hartman
maintainerPATCH 212/294 net/sched: act_skbmod: prevent kernel-infoleak
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Dumazet <[email protected]>
commit d313eb8b77557a6d5855f42d2234bd592c7b50dd upstream.
syzbot found that tcf_skbmod_dump() was copying four bytes from kernel stack to user space [1].
The issue here is that 'struct tc_skbmod' has a four bytes hole.
We need to clear the structure before filling fields.
[1]
BUG: KMSAN: kernel-infoleak in instrument_copy_to_user include/linux/instrumented.h:114 [inline] BUG: KMSAN: kernel-infoleak in copy_to_user_iter lib/iov_iter.c:24 [inline] BUG: KMSAN: kernel-infoleak in iterate_ubuf include/linux/iov_iter.h:29 [inline] BUG: KMSAN: kernel-infoleak in iterate_and_advance2 include/linux/iov_iter.h:245 [inline] BUG: KMSAN: kernel-infoleak in iterate_and_advance include/linux/iov_iter.h:271 [inline] BUG: KMSAN: kernel-infoleak in _copy_to_iter+0x366/0x2520 lib/iov_iter.c:185 instrument_copy_to_user include/linux/instrumented.h:114 [inline] copy_to_user_iter lib/iov_iter.c:24 [inline] iterate_ubuf include/linux/iov_iter.h:29 [inline] iterate_and_advance2 include/linux/iov_iter.h:245 [inline] iterate_and_advance include/linux/iov_iter.h:271 [inline] _copy_to_iter+0x366/0x2520 lib/iov_iter.c:185 copy_to_iter include/linux/uio.h:196 [inline] simple_copy_to_iter net/core/datagram.c:532 [inline] __skb_datagram_iter+0x185/0x1000 net/core/datagram.c:420 skb_copy_datagram_iter+0x5c/0x200 net/core/datagram.c:546 skb_copy_datagram_msg include/linux/skbuff.h:4050 [inline] netlink_recvmsg+0x432/0x1610 net/netlink/af_netlink.c:1962 sock_recvmsg_nosec net/socket.c:1046 [inline] sock_recvmsg+0x2c4/0x340 net/socket.c:1068 __sys_recvfrom+0x35a/0x5f0 net/socket.c:2242 __do_sys_recvfrom net/socket.c:2260 [inline] __se_sys_recvfrom net/socket.c:2256 [inline] __x64_sys_recvfrom+0x126/0x1d0 net/socket.c:2256 do_syscall_64+0xd5/0x1f0 entry_SYSCALL_64_after_hwframe+0x6d/0x75
Uninit was stored to memory at:
pskb_expand_head+0x30f/0x19d0 net/core/skbuff.c:2253 netlink_trim+0x2c2/0x330 net/netlink/af_netlink.c:1317 netlink_unicast+0x9f/0x1260 net/netlink/af_netlink.c:1351 nlmsg_unicast include/net/netlink.h:1144 [inline] nlmsg_notify+0x21d/0x2f0 net/netlink/af_netlink.c:2610 rtnetlink_send+0x73/0x90 net/core/rtnetlink.c:741 rtnetlink_maybe_send include/linux/rtnetlink.h:17 [inline] tcf_add_notify net/sched/act_api.c:2048 [inline] tcf_action_add net/sched/act_api.c:2071 [inline] tc_ctl_action+0x146e/0x19d0 net/sched/act_api.c:2119 rtnetlink_rcv_msg+0x1737/0x1900 net/core/rtnetlink.c:6595 netlink_rcv_skb+0x375/0x650 net/netlink/af_netlink.c:2559 rtnetlink_rcv+0x34/0x40 net/core/rtnetlink.c:6613 netlink_unicast_kernel net/netlink/af_netlink.c:1335 [inline] netlink_unicast+0xf4c/0x1260 net/netlink/af_netlink.c:1361 netlink_sendmsg+0x10df/0x11f0 net/netlink/af_netlink.c:1905 sock_sendmsg_nosec net/socket.c:730 [inline] __sock_sendmsg+0x30f/0x380 net/socket.c:745 ____sys_sendmsg+0x877/0xb60 net/socket.c:2584 ___sys_sendmsg+0x28d/0x3c0 net/socket.c:2638 __sys_sendmsg net/socket.c:2667 [inline] __do_sys_sendmsg net/socket.c:2676 [inline] __se_sys_sendmsg net/socket.c:2674 [inline] __x64_sys_sendmsg+0x307/0x4a0 net/socket.c:2674 do_syscall_64+0xd5/0x1f0 entry_SYSCALL_64_after_hwframe+0x6d/0x75
Uninit was stored to memory at:
__nla_put lib/nlattr.c:1041 [inline] nla_put+0x1c6/0x230 lib/nlattr.c:1099 tcf_skbmod_dump+0x23f/0xc20 net/sched/act_skbmod.c:256 tcf_action_dump_old net/sched/act_api.c:1191 [inline] tcf_action_dump_1+0x85e/0x970 net/sched/act_api.c:1227 tcf_action_dump+0x1fd/0x460 net/sched/act_api.c:1251 tca_get_fill+0x519/0x7a0 net/sched/act_api.c:1628 tcf_add_notify_msg net/sched/act_api.c:2023 [inline] tcf_add_notify net/sched/act_api.c:2042 [inline] tcf_action_add net/sched/act_api.c:2071 [inline] tc_ctl_action+0x1365/0x19d0 net/sched/act_api.c:2119 rtnetlink_rcv_msg+0x1737/0x1900 net/core/rtnetlink.c:6595 netlink_rcv_skb+0x375/0x650 net/netlink/af_netlink.c:2559 rtnetlink_rcv+0x34/0x40 net/core/rtnetlink.c:6613 netlink_unicast_kernel net/netlink/af_netlink.c:1335 [inline] netlink_unicast+0xf4c/0x1260 net/netlink/af_netlink.c:1361 netlink_sendmsg+0x10df/0x11f0 net/netlink/af_netlink.c:1905 sock_sendmsg_nosec net/socket.c:730 [inline] __sock_sendmsg+0x30f/0x380 net/socket.c:745 ____sys_sendmsg+0x877/0xb60 net/socket.c:2584 ___sys_sendmsg+0x28d/0x3c0 net/socket.c:2638 __sys_sendmsg net/socket.c:2667 [inline] __do_sys_sendmsg net/socket.c:2676 [inline] __se_sys_sendmsg net/socket.c:2674 [inline] __x64_sys_sendmsg+0x307/0x4a0 net/socket.c:2674 do_syscall_64+0xd5/0x1f0 entry_SYSCALL_64_after_hwframe+0x6d/0x75
Local variable opt created at:
tcf_skbmod_dump+0x9d/0xc20 net/sched/act_skbmod.c:244 tcf_action_dump_old net/sched/act_api.c:1191 [inline] tcf_action_dump_1+0x85e/0x970 net/sched/act_api.c:1227
Bytes 188-191 of 248 are uninitialized Memory access of size 248 starts at ffff888117697680 Data copied to user address 00007ffe56d855f0
--- net/sched/act_skbmod.c | 10 +++++----- 1 file changed, 5 insertions(+), 5 deletions(-)
net/sched/act_skbmod.c +5 -5
@@ -219,13 +219,13 @@ static int tcf_skbmod_dump(struct sk_bufstruct tcf_skbmod *d =to_skbmod (a);unsigned char *b =skb_tail_pointer (skb);struct tcf_skbmod_params *p; -struct tc_skbmod opt = { - .index = d->tcf_index, - .refcnt =refcount_read (&d->tcf_refcnt) - ref, - .bindcnt =atomic_read (&d->tcf_bindcnt) - bind, - }; +struct tc_skbmod opt;struct tcf_t t; +memset (&opt,0 ,sizeof (opt)); + opt.index = d->tcf_index; + opt.refcnt =refcount_read (&d->tcf_refcnt) - ref, + opt.bindcnt =atomic_read (&d->tcf_bindcnt) - bind;spin_lock_bh (&d->tcf_lock); opt.action = d->tcf_action; p = rcu_dereference_protected(d->skbmod_p,
Greg Kroah-Hartman
maintainerPATCH 213/294 net: stmmac: fix rx queue priority assignment
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Piotr Wejman <[email protected]>
commit b3da86d432b7cd65b025a11f68613e333d2483db upstream.
The driver should ensure that same priority is not mapped to multiple rx queues. From DesignWare Cores Ethernet Quality-of-Service Databook, section 17.1.29 MAC_RxQ_Ctrl2:
"[...]The software must ensure that the content of this field is mutually exclusive to the PSRQ fields for other queues, that is, the same priority is not mapped to multiple Rx queues[...]"
Previously rx_queue_priority() function was:
- clearing all priorities from a queue
- adding new priorities to that queue
After this patch it will:
- first assign new priorities to a queue
- then remove those priorities from all other queues
- keep other priorities previously assigned to that queue
--- drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c | 40 +++++++++++++++----- drivers/net/ethernet/stmicro/stmmac/dwxgmac2_core.c | 38 +++++++++++++++---- 2 files changed, 62 insertions(+), 16 deletions(-)
drivers/net/ethernet/stmicro/stmmac/dwmac4_core.c +31 -9
@@ -75,19 +75,41 @@ static void dwmac4_rx_queue_priority(str u32 prio, u32 queue) { void __iomem *ioaddr = hw->pcsr; -u32 base_register; -u32 value; +u32 clear_mask =0 ; +u32 ctrl2, ctrl3; +int i; - base_register = (queue <4 ) ?GMAC_RXQ_CTRL2 :GMAC_RXQ_CTRL3 ; -if (queue >=4 ) - queue -=4 ; + ctrl2 =readl (ioaddr +GMAC_RXQ_CTRL2 ); + ctrl3 =readl (ioaddr +GMAC_RXQ_CTRL3 ); + +/* The software must ensure that the same priority +* is not mapped to multiple Rx queues +*/ +for (i =0 ; i <4 ; i++) + clear_mask |= ((prio <<GMAC_RXQCTRL_PSRQX_SHIFT (i)) & +GMAC_RXQCTRL_PSRQX_MASK (i)); - value =readl (ioaddr + base_register); + ctrl2 &= ~clear_mask; + ctrl3 &= ~clear_mask; - value &= ~GMAC_RXQCTRL_PSRQX_MASK (queue); - value |= (prio <<GMAC_RXQCTRL_PSRQX_SHIFT (queue)) & +/* First assign new priorities to a queue, then +* clear them from others queues +*/ +if (queue <4 ) { + ctrl2 |= (prio <<GMAC_RXQCTRL_PSRQX_SHIFT (queue)) &GMAC_RXQCTRL_PSRQX_MASK (queue); -writel (value, ioaddr + base_register); + +writel (ctrl2, ioaddr +GMAC_RXQ_CTRL2 ); +writel (ctrl3, ioaddr +GMAC_RXQ_CTRL3 ); + }else { + queue -=4 ; + + ctrl3 |= (prio <<GMAC_RXQCTRL_PSRQX_SHIFT (queue)) & +GMAC_RXQCTRL_PSRQX_MASK (queue); + +writel (ctrl3, ioaddr +GMAC_RXQ_CTRL3 ); +writel (ctrl2, ioaddr +GMAC_RXQ_CTRL2 ); + } } static void dwmac4_tx_queue_priority(struct mac_device_info *hw,
drivers/net/ethernet/stmicro/stmmac/dwxgmac2_core.c +31 -7
@@ -97,17 +97,41 @@ static void dwxgmac2_rx_queue_prio(struc u32 queue) {void __iomem *ioaddr = hw->pcsr; -u32 value, reg; +u32 clear_mask =0 ; +u32 ctrl2, ctrl3; +int i; - reg = (queue <4 ) ?XGMAC_RXQ_CTRL2 :XGMAC_RXQ_CTRL3 ; -if (queue >=4 ) + ctrl2 =readl (ioaddr +XGMAC_RXQ_CTRL2 ); + ctrl3 =readl (ioaddr +XGMAC_RXQ_CTRL3 ); + +/* The software must ensure that the same priority +* is not mapped to multiple Rx queues +*/ +for (i =0 ; i <4 ; i++) + clear_mask |= ((prio <<XGMAC_PSRQ_SHIFT (i)) & +XGMAC_PSRQ (i)); + + ctrl2 &= ~clear_mask; + ctrl3 &= ~clear_mask; + +/* First assign new priorities to a queue, then +* clear them from others queues +*/ +if (queue <4 ) { + ctrl2 |= (prio <<XGMAC_PSRQ_SHIFT (queue)) & +XGMAC_PSRQ (queue); + +writel (ctrl2, ioaddr +XGMAC_RXQ_CTRL2 ); +writel (ctrl3, ioaddr +XGMAC_RXQ_CTRL3 ); + }else { queue -=4 ; - value =readl (ioaddr + reg); - value &= ~XGMAC_PSRQ (queue); - value |= (prio <<XGMAC_PSRQ_SHIFT (queue)) &XGMAC_PSRQ (queue); + ctrl3 |= (prio <<XGMAC_PSRQ_SHIFT (queue)) & +XGMAC_PSRQ (queue); -writel (value, ioaddr + reg); +writel (ctrl3, ioaddr +XGMAC_RXQ_CTRL3 ); +writel (ctrl2, ioaddr +XGMAC_RXQ_CTRL2 ); + } } static void dwxgmac2_tx_queue_prio(struct mac_device_info *hw, u32 prio,
Greg Kroah-Hartman
maintainerPATCH 214/294 erspan: make sure erspan_base_hdr is present in skb->head
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Dumazet <[email protected]>
commit 17af420545a750f763025149fa7b833a4fc8b8f0 upstream.
syzbot reported a problem in ip6erspan_rcv() [1]
Issue is that ip6erspan_rcv() (and erspan_rcv()) no longer make sure erspan_base_hdr is present in skb linear part (skb->head) before getting @ver field from it.
Add the missing pskb_may_pull() calls.
v2: Reload iph pointer in erspan_rcv() after pskb_may_pull()
because skb->head might have changed.
[1]
BUG: KMSAN: uninit-value in pskb_may_pull_reason include/linux/skbuff.h:2742 [inline] BUG: KMSAN: uninit-value in pskb_may_pull include/linux/skbuff.h:2756 [inline] BUG: KMSAN: uninit-value in ip6erspan_rcv net/ipv6/ip6_gre.c:541 [inline] BUG: KMSAN: uninit-value in gre_rcv+0x11f8/0x1930 net/ipv6/ip6_gre.c:610 pskb_may_pull_reason include/linux/skbuff.h:2742 [inline] pskb_may_pull include/linux/skbuff.h:2756 [inline] ip6erspan_rcv net/ipv6/ip6_gre.c:541 [inline] gre_rcv+0x11f8/0x1930 net/ipv6/ip6_gre.c:610 ip6_protocol_deliver_rcu+0x1d4c/0x2ca0 net/ipv6/ip6_input.c:438 ip6_input_finish net/ipv6/ip6_input.c:483 [inline] NF_HOOK include/linux/netfilter.h:314 [inline] ip6_input+0x15d/0x430 net/ipv6/ip6_input.c:492 ip6_mc_input+0xa7e/0xc80 net/ipv6/ip6_input.c:586 dst_input include/net/dst.h:460 [inline] ip6_rcv_finish+0x955/0x970 net/ipv6/ip6_input.c:79 NF_HOOK include/linux/netfilter.h:314 [inline] ipv6_rcv+0xde/0x390 net/ipv6/ip6_input.c:310 __netif_receive_skb_one_core net/core/dev.c:5538 [inline] __netif_receive_skb+0x1da/0xa00 net/core/dev.c:5652 netif_receive_skb_internal net/core/dev.c:5738 [inline] netif_receive_skb+0x58/0x660 net/core/dev.c:5798 tun_rx_batched+0x3ee/0x980 drivers/net/tun.c:1549 tun_get_user+0x5566/0x69e0 drivers/net/tun.c:2002 tun_chr_write_iter+0x3af/0x5d0 drivers/net/tun.c:2048 call_write_iter include/linux/fs.h:2108 [inline] new_sync_write fs/read_write.c:497 [inline] vfs_write+0xb63/0x1520 fs/read_write.c:590 ksys_write+0x20f/0x4c0 fs/read_write.c:643 __do_sys_write fs/read_write.c:655 [inline] __se_sys_write fs/read_write.c:652 [inline] __x64_sys_write+0x93/0xe0 fs/read_write.c:652 do_syscall_64+0xd5/0x1f0 entry_SYSCALL_64_after_hwframe+0x6d/0x75
Uninit was created at:
slab_post_alloc_hook mm/slub.c:3804 [inline] slab_alloc_node mm/slub.c:3845 [inline] kmem_cache_alloc_node+0x613/0xc50 mm/slub.c:3888 kmalloc_reserve+0x13d/0x4a0 net/core/skbuff.c:577 __alloc_skb+0x35b/0x7a0 net/core/skbuff.c:668 alloc_skb include/linux/skbuff.h:1318 [inline] alloc_skb_with_frags+0xc8/0xbf0 net/core/skbuff.c:6504 sock_alloc_send_pskb+0xa81/0xbf0 net/core/sock.c:2795 tun_alloc_skb drivers/net/tun.c:1525 [inline] tun_get_user+0x209a/0x69e0 drivers/net/tun.c:1846 tun_chr_write_iter+0x3af/0x5d0 drivers/net/tun.c:2048 call_write_iter include/linux/fs.h:2108 [inline] new_sync_write fs/read_write.c:497 [inline] vfs_write+0xb63/0x1520 fs/read_write.c:590 ksys_write+0x20f/0x4c0 fs/read_write.c:643 __do_sys_write fs/read_write.c:655 [inline] __se_sys_write fs/read_write.c:652 [inline] __x64_sys_write+0x93/0xe0 fs/read_write.c:652 do_syscall_64+0xd5/0x1f0 entry_SYSCALL_64_after_hwframe+0x6d/0x75 CPU: 1 PID: 5045 Comm: syz-executor114 Not tainted 6.9.0-rc1-syzkaller-00021-g962490525cff #0
--- net/ipv4/ip_gre.c | 5 +++++ net/ipv6/ip6_gre.c | 3 +++ 2 files changed, 8 insertions(+)
net/ipv4/ip_gre.c +5 -0
@@ -278,8 +278,13 @@ static int erspan_rcv(struct sk_buff *sk tpi->flags |TUNNEL_NO_KEY , iph->saddr, iph->daddr, 0); }else { +if (unlikely (!pskb_may_pull (skb, + gre_hdr_len +sizeof (*ershdr)))) +return PACKET_REJECT ; + ershdr = (struct erspan_base_hdr *)(skb->data + gre_hdr_len); ver = ershdr->ver; + iph =ip_hdr (skb); tunnel =ip_tunnel_lookup (itn, skb->dev->ifindex, tpi->flags |TUNNEL_KEY , iph->saddr, iph->daddr, tpi->key);
net/ipv6/ip6_gre.c +3 -0
@@ -533,6 +533,9 @@ static int ip6erspan_rcv(struct sk_buffstruct ip6_tnl *tunnel;u8 ver; +if (unlikely (!pskb_may_pull (skb,sizeof (*ershdr)))) +return PACKET_REJECT ; + ipv6h =ipv6_hdr (skb); ershdr = (struct erspan_base_hdr *)skb->data; ver = ershdr->ver;
Greg Kroah-Hartman
maintainerPATCH 215/294 selftests: reuseaddr_conflict: add missing new line at the end of the output
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jakub Kicinski <[email protected]>
commit 31974122cfdeaf56abc18d8ab740d580d9833e90 upstream.
The netdev CI runs in a VM and captures serial, so stdout and stderr get combined. Because there's a missing new line in stderr the test ends up corrupting KTAP:
# Successok 1 selftests: net: reuseaddr_conflict
which should have been:
# Success
ok 1 selftests: net: reuseaddr_conflict
--- tools/testing/selftests/net/reuseaddr_conflict.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
tools/testing/selftests/net/reuseaddr_conflict.c +1 -1
@@ -109,6 +109,6 @@ int main(void) fd1 =open_port (0 ,1 );if (fd1 >=0 )error (1 ,0 ,"Was allowed to create an ipv4 reuseport on an already bound non-reuseport socket with no ipv6" ); -fprintf (stderr,"Success" ); +fprintf (stderr,"Success\n" );return 0 ; }
Greg Kroah-Hartman
maintainerPATCH 216/294 ipv6: Fix infinite recursion in fib6_dump_done().
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kuniyuki Iwashima <[email protected]>
commit d21d40605bca7bd5fc23ef03d4c1ca1f48bc2cae upstream.
syzkaller reported infinite recursive calls of fib6_dump_done() during netlink socket destruction. [1]
Quoted 1 line
From the log, syzkaller sent an
AF_UNSPECRTM_GETROUTEmessage, and then
the response was generated. The following recvmmsg() resumed the dump for IPv6, but the first call of inet6_dump_fib() failed at kzalloc() due to the fault injection. [0]
12:01:34 executing program 3:
r0 = socket$nl_route(0x10, 0x3, 0x0)
sendmsg$nl_route(r0, ... snip ...)
recvmmsg(r0, ... snip ...) (fail_nth: 8)
Here, fib6_dump_done() was set to nlk_sk(sk)->cb.done, and the next call of inet6_dump_fib() set it to nlk_sk(sk)->cb.args[3]. syzkaller stopped receiving the response halfway through, and finally netlink_sock_destruct() called nlk_sk(sk)->cb.done().
fib6_dump_done() calls fib6_dump_end() and nlk_sk(sk)->cb.done() if it is still not NULL. fib6_dump_end() rewrites nlk_sk(sk)->cb.done() by nlk_sk(sk)->cb.args[3], but it has the same function, not NULL, calling itself recursively and hitting the stack guard page.
To avoid the issue, let's set the destructor after kzalloc().
[0]:FAULT_INJECTION: forcing a failure.
name failslab, interval 1, probability 0, space 0, times 0
CPU: 1 PID: 432110 Comm: syz-executor.3 Not tainted 6.8.0-12821-g537c2e91d354-dirty #11 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.16.0-0-gd239552ce722-prebuilt.qemu.org 04/01/2014 Call Trace: <TASK> dump_stack_lvl (lib/dump_stack.c:117) should_fail_ex (lib/fault-inject.c:52 lib/fault-inject.c:153) should_failslab (mm/slub.c:3733) kmalloc_trace (mm/slub.c:3748 mm/slub.c:3827 mm/slub.c:3992) inet6_dump_fib (./include/linux/slab.h:628 ./include/linux/slab.h:749 net/ipv6/ip6_fib.c:662) rtnl_dump_all (net/core/rtnetlink.c:4029) netlink_dump (net/netlink/af_netlink.c:2269) netlink_recvmsg (net/netlink/af_netlink.c:1988) ____sys_recvmsg (net/socket.c:1046 net/socket.c:2801) ___sys_recvmsg (net/socket.c:2846) do_recvmmsg (net/socket.c:2943) __x64_sys_recvmmsg (net/socket.c:3041 net/socket.c:3034 net/socket.c:3034)
[1]:
BUG: TASK stack guard page was hit at 00000000f2fa9af1 (stack is 00000000b7912430..000000009a436beb) stack guard page: 0000 [#1] PREEMPT SMP KASAN CPU: 1 PID: 223719 Comm: kworker/1:3 Not tainted 6.8.0-12821-g537c2e91d354-dirty #11 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.16.0-0-gd239552ce722-prebuilt.qemu.org 04/01/2014 Workqueue: events netlink_sock_destruct_work RIP: 0010:fib6_dump_done (net/ipv6/ip6_fib.c:570) Code: 3c 24 e8 f3 e9 51 fd e9 28 fd ff ff 66 66 2e 0f 1f 84 00 00 00 00 00 0f 1f 00 f3 0f 1e fa 41 57 41 56 41 55 41 54 55 48 89 fd <53> 48 8d 5d 60 e8 b6 4d 07 fd 48 89 da 48 b8 00 00 00 00 00 fc ff RSP: 0018:ffffc9000d980000 EFLAGS: 00010293 RAX: 0000000000000000 RBX: ffffffff84405990 RCX: ffffffff844059d3 RDX: ffff8881028e0000 RSI: ffffffff84405ac2 RDI: ffff88810c02f358 RBP: ffff88810c02f358 R08: 0000000000000007 R09: 0000000000000000 R10: 0000000000000000 R11: 0000000000000224 R12: 0000000000000000 R13: ffff888007c82c78 R14: ffff888007c82c68 R15: ffff888007c82c68 FS: 0000000000000000(0000) GS:ffff88811b100000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: ffffc9000d97fff8 CR3: 0000000102309002 CR4: 0000000000770ef0 PKRU: 55555554 Call Trace: <#DF> </#DF> <TASK> fib6_dump_done (net/ipv6/ip6_fib.c:572 (discriminator 1)) fib6_dump_done (net/ipv6/ip6_fib.c:572 (discriminator 1)) ... fib6_dump_done (net/ipv6/ip6_fib.c:572 (discriminator 1)) fib6_dump_done (net/ipv6/ip6_fib.c:572 (discriminator 1)) netlink_sock_destruct (net/netlink/af_netlink.c:401) __sk_destruct (net/core/sock.c:2177 (discriminator 2)) sk_destruct (net/core/sock.c:2224) __sk_free (net/core/sock.c:2235) sk_free (net/core/sock.c:2246) process_one_work (kernel/workqueue.c:3259) worker_thread (kernel/workqueue.c:3329 kernel/workqueue.c:3416) kthread (kernel/kthread.c:388) ret_from_fork (arch/x86/kernel/process.c:153) ret_from_fork_asm (arch/x86/entry/entry_64.S:256) Modules linked in:
--- net/ipv6/ip6_fib.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-)
net/ipv6/ip6_fib.c +7 -7
@@ -643,19 +643,19 @@ static int inet6_dump_fib(struct sk_buffif (!w) {/* New dump: * -* 1. hook callback destructor. -*/ - cb->args[3 ] = (long )cb->done; - cb->done = fib6_dump_done; - -/* -* 2. allocate and initialize walker. +* 1. allocate and initialize walker. */ w =kzalloc (sizeof (*w),GFP_ATOMIC );if (!w)return -ENOMEM ; w->func = fib6_dump_node; cb->args[2 ] = (long )w; + +/* 2. hook callback destructor. +*/ + cb->args[3 ] = (long )cb->done; + cb->done = fib6_dump_done; + } arg.skb = skb;
Greg Kroah-Hartman
maintainerPATCH 217/294 udp: do not transition UDP GRO fraglist partial checksums to unnecessary
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Antoine Tenart <[email protected]>
commit f0b8c30345565344df2e33a8417a27503589247d upstream.
UDP GRO validates checksums and in udp4/6_gro_complete fraglist packets are converted to CHECKSUM_UNNECESSARY to avoid later checks. However this is an issue for CHECKSUM_PARTIAL packets as they can be looped in an egress path and then their partial checksums are not fixed.
Different issues can be observed, from invalid checksum on packets to traces like:
gen01: hw csum failure
skb len=3008 headroom=160 headlen=1376 tailroom=0 mac=(106,14) net=(120,40) trans=160 shinfo(txflags=0 nr_frags=0 gso(size=0 type=0 segs=0)) csum(0xffff232e ip_summed=2 complete_sw=0 valid=0 level=0) hash(0x77e3d716 sw=1 l4=1) proto=0x86dd pkttype=0 iif=12
...
Fix this by only converting CHECKSUM_NONE packets to CHECKSUM_UNNECESSARY by reusing __skb_incr_checksum_unnecessary. All other checksum types are kept as-is, including CHECKSUM_COMPLETE as fraglist packets being segmented back would have their skb->csum valid.
--- net/ipv4/udp_offload.c | 8 +------- net/ipv6/udp_offload.c | 8 +------- 2 files changed, 2 insertions(+), 14 deletions(-)
net/ipv4/udp_offload.c +1 -7
@@ -668,13 +668,7 @@ INDIRECT_CALLABLE_SCOPE int udp4_gro_comskb_shinfo (skb)->gso_type |= (SKB_GSO_FRAGLIST |SKB_GSO_UDP_L4 );skb_shinfo (skb)->gso_segs =NAPI_GRO_CB (skb)->count; -if (skb->ip_summed ==CHECKSUM_UNNECESSARY ) { -if (skb->csum_level <SKB_MAX_CSUM_LEVEL ) - skb->csum_level++; - }else { - skb->ip_summed =CHECKSUM_UNNECESSARY ; - skb->csum_level =0 ; - } +__skb_incr_checksum_unnecessary (skb);return 0 ; }
net/ipv6/udp_offload.c +1 -7
@@ -169,13 +169,7 @@ INDIRECT_CALLABLE_SCOPE int udp6_gro_comskb_shinfo (skb)->gso_type |= (SKB_GSO_FRAGLIST |SKB_GSO_UDP_L4 );skb_shinfo (skb)->gso_segs =NAPI_GRO_CB (skb)->count; -if (skb->ip_summed ==CHECKSUM_UNNECESSARY ) { -if (skb->csum_level <SKB_MAX_CSUM_LEVEL ) - skb->csum_level++; - }else { - skb->ip_summed =CHECKSUM_UNNECESSARY ; - skb->csum_level =0 ; - } +__skb_incr_checksum_unnecessary (skb);return 0 ; }
Greg Kroah-Hartman
maintainerPATCH 218/294 octeontx2-pf: check negative error code in otx2_open()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Su Hui <[email protected]>
commit e709acbd84fb6ef32736331b0147f027a3ef4c20 upstream.
otx2_rxtx_enable() return negative error code such as -EIO, check -EIO rather than EIO to fix this problem.
--- drivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/net/ethernet/marvell/octeontx2/nic/otx2_pf.c +1 -1
@@ -1598,7 +1598,7 @@ int otx2_open(struct net_device *netdev)* mcam entries are enabled to receive the packets. Hence disable the * packet I/O. */ -if (err ==EIO ) +if (err == -EIO ) goto err_disable_rxtx;else if (err) goto err_tx_stop_queues;
Greg Kroah-Hartman
maintainerPATCH 219/294 i40e: fix i40e_count_filters() to count only active/new filters
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Aleksandr Loktionov <[email protected]>
commit eb58c598ce45b7e787568fe27016260417c3d807 upstream.
The bug usually affects untrusted VFs, because they are limited to 18 MACs, it affects them badly, not letting to create MAC all filters. Not stable to reproduce, it happens when VF user creates MAC filters when other MACVLAN operations are happened in parallel.
But consequence is that VF can't receive desired traffic.
Fix counter to be bumped only for new or active filters.
--- drivers/net/ethernet/intel/i40e/i40e_main.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/net/ethernet/intel/i40e/i40e_main.c +5 -2
@@ -1230,8 +1230,11 @@ int i40e_count_filters(struct i40e_vsi *int bkt;int cnt =0 ; -hash_for_each_safe (vsi->mac_filter_hash, bkt, h, f, hlist) - ++cnt; +hash_for_each_safe (vsi->mac_filter_hash, bkt, h, f, hlist) { +if (f->state ==I40E_FILTER_NEW || + f->state ==I40E_FILTER_ACTIVE ) + ++cnt; + }return cnt; }
Greg Kroah-Hartman
maintainerPATCH 220/294 i40e: fix vf may be used uninitialized in this function warning
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Aleksandr Loktionov <[email protected]>
commit f37c4eac99c258111d414d31b740437e1925b8e8 upstream.
To fix the regression introduced by commit 52424f974bc5, which causes servers hang in very hard to reproduce conditions with resets races. Using two sources for the information is the root cause.
In this function before the fix bumping v didn't mean bumping vf pointer. But the code used this variables interchangeably, so stale vf could point to different/not intended vf.
Remove redundant "v" variable and iterate via single VF pointer across whole function instead to guarantee VF pointer validity.
--- drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c | 34 +++++++++------------ 1 file changed, 16 insertions(+), 18 deletions(-)
drivers/net/ethernet/intel/i40e/i40e_virtchnl_pf.c +16 -18
@@ -1573,8 +1573,8 @@ bool i40e_reset_all_vfs(struct i40e_pf * {struct i40e_hw *hw = &pf->hw;struct i40e_vf *vf; -int i, v;u32 reg; +int i;/* If we don't have any VFs, then there is nothing to reset */ if (!pf->num_alloc_vfs)
@@ -1585,11 +1585,10 @@ bool i40e_reset_all_vfs(struct i40e_pf *return false;/* Begin reset on all VFs at once */ -for (v =0 ; v < pf->num_alloc_vfs; v++) { - vf = &pf->vf[v]; +for (vf = &pf->vf[0 ]; vf < &pf->vf[pf->num_alloc_vfs]; ++vf) {/* If VF is being reset no need to trigger reset again */ if (!test_bit (I40E_VF_STATE_RESETTING , &vf->vf_states)) -i40e_trigger_vf_reset (&pf->vf[v], flr); +i40e_trigger_vf_reset (vf, flr); }/* HW requires some time to make sure it can flush the FIFO for a VF
@@ -1598,14 +1597,13 @@ bool i40e_reset_all_vfs(struct i40e_pf ** the VFs using a simple iterator that increments once that VF has * finished resetting. */ -for (i =0 , v =0 ; i <10 && v < pf->num_alloc_vfs; i++) { +for (i =0 , vf = &pf->vf[0 ]; i <10 && vf < &pf->vf[pf->num_alloc_vfs]; ++i) {usleep_range (10000 ,20000 );/* Check each VF in sequence, beginning with the VF to fail * the previous check. */ -while (v < pf->num_alloc_vfs) { - vf = &pf->vf[v]; +while (vf < &pf->vf[pf->num_alloc_vfs]) {if (!test_bit (I40E_VF_STATE_RESETTING , &vf->vf_states)) { reg =rd32 (hw,I40E_VPGEN_VFRSTAT (vf->vf_id));if (!(reg &I40E_VPGEN_VFRSTAT_VFRD_MASK ))
@@ -1615,7 +1613,7 @@ bool i40e_reset_all_vfs(struct i40e_pf */* If the current VF has finished resetting, move on * to the next VF in sequence. */ - v++; + ++vf; } }
@@ -1625,39 +1623,39 @@ bool i40e_reset_all_vfs(struct i40e_pf */* Display a warning if at least one VF didn't manage to reset in * time, but continue on with the operation. */ -if (v < pf->num_alloc_vfs) +if (vf < &pf->vf[pf->num_alloc_vfs])dev_err (&pf->pdev->dev,"VF reset check timeout on VF %d\n" , - pf->vf[v].vf_id); + vf->vf_id);usleep_range (10000 ,20000 );/* Begin disabling all the rings associated with VFs, but do not wait * between each VF. */ -for (v =0 ; v < pf->num_alloc_vfs; v++) { +for (vf = &pf->vf[0 ]; vf < &pf->vf[pf->num_alloc_vfs]; ++vf) {/* On initial reset, we don't have any queues to disable */ -if (pf->vf[v].lan_vsi_idx ==0 ) +if (vf->lan_vsi_idx ==0 )continue ;/* If VF is reset in another thread just continue */ if (test_bit (I40E_VF_STATE_RESETTING , &vf->vf_states))continue ; -i40e_vsi_stop_rings_no_wait (pf->vsi[pf->vf[v].lan_vsi_idx]); +i40e_vsi_stop_rings_no_wait (pf->vsi[vf->lan_vsi_idx]); }/* Now that we've notified HW to disable all of the VF rings, wait * until they finish. */ -for (v =0 ; v < pf->num_alloc_vfs; v++) { +for (vf = &pf->vf[0 ]; vf < &pf->vf[pf->num_alloc_vfs]; ++vf) {/* On initial reset, we don't have any queues to disable */ -if (pf->vf[v].lan_vsi_idx ==0 ) +if (vf->lan_vsi_idx ==0 )continue ;/* If VF is reset in another thread just continue */ if (test_bit (I40E_VF_STATE_RESETTING , &vf->vf_states))continue ; -i40e_vsi_wait_queues_disabled (pf->vsi[pf->vf[v].lan_vsi_idx]); +i40e_vsi_wait_queues_disabled (pf->vsi[vf->lan_vsi_idx]); }/* Hw may need up to 50ms to finish disabling the RX queues. We
@@ -1666,12 +1664,12 @@ bool i40e_reset_all_vfs(struct i40e_pf *mdelay (50 );/* Finish the reset on each VF */ -for (v =0 ; v < pf->num_alloc_vfs; v++) { +for (vf = &pf->vf[0 ]; vf < &pf->vf[pf->num_alloc_vfs]; ++vf) {/* If VF is reset in another thread just continue */ if (test_bit (I40E_VF_STATE_RESETTING , &vf->vf_states))continue ; -i40e_cleanup_reset_vf (&pf->vf[v]); +i40e_cleanup_reset_vf (vf); }i40e_flush (hw);
Greg Kroah-Hartman
maintainerPATCH 221/294 scsi: qla2xxx: Update manufacturer details
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bikash Hazarika <[email protected]>
[ Upstream commit 1ccad27716ecad1fd58c35e579bedb81fa5e1ad5 ]
Update manufacturer details to indicate Marvell Semiconductors.
Stable-dep-of: 688fa069fda6 ("scsi: qla2xxx: Update manufacturer detail")
--- drivers/scsi/qla2xxx/qla_def.h | 2 +- drivers/scsi/qla2xxx/qla_gs.c | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-)
drivers/scsi/qla2xxx/qla_def.h +1 -1
@@ -56,7 +56,7 @@ typedef struct {#include "qla_nvme.h" #define QLA2XXX_DRIVER_NAME "qla2xxx"#define QLA2XXX_APIDEV "ql2xapidev" -#define QLA2XXX_MANUFACTURER "QLogic Corporation" +#define QLA2XXX_MANUFACTURER "Marvell Semiconductor, Inc."/* * We have MAILBOX_REGISTER_COUNT sized arrays in a few places,
drivers/scsi/qla2xxx/qla_gs.c +1 -1
@@ -1614,7 +1614,7 @@ qla2x00_hba_attributes(scsi_qla_host_t *vha, void *entries, eiter->type =cpu_to_be16 (FDMI_HBA_MANUFACTURER ); alen =scnprintf ( eiter->a.manufacturer,sizeof (eiter->a.manufacturer), -"%s" ,"QLogic Corporation" ); +"%s" ,QLA2XXX_MANUFACTURER ); alen +=FDMI_ATTR_ALIGNMENT (alen); alen +=FDMI_ATTR_TYPELEN (eiter); eiter->len =cpu_to_be16 (alen);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 222/294 scsi: qla2xxx: Update manufacturer detail
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Bikash Hazarika <[email protected]>
[ Upstream commit 688fa069fda6fce24d243cddfe0c7024428acb74 ]
Update manufacturer detail from "Marvell Semiconductor, Inc." to "Marvell".
--- drivers/scsi/qla2xxx/qla_def.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/scsi/qla2xxx/qla_def.h +1 -1
@@ -56,7 +56,7 @@ typedef struct {#include "qla_nvme.h" #define QLA2XXX_DRIVER_NAME "qla2xxx"#define QLA2XXX_APIDEV "ql2xapidev" -#define QLA2XXX_MANUFACTURER "Marvell Semiconductor, Inc." +#define QLA2XXX_MANUFACTURER "Marvell"/* * We have MAILBOX_REGISTER_COUNT sized arrays in a few places,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 223/294 Revert "usb: phy: generic: Get the vbus supply"
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alexander Stein <[email protected]>
[ Upstream commit fdada0db0b2ae2addef4ccafe50937874dbeeebe ]
This reverts commit 75fd6485cccef269ac9eb3b71cf56753341195ef. This patch was applied twice by accident, causing probe failures. Revert the accident.
--- drivers/usb/phy/phy-generic.c | 7 ------- 1 file changed, 7 deletions(-)
drivers/usb/phy/phy-generic.c +0 -7
@@ -268,13 +268,6 @@ int usb_phy_gen_create_phy(struct device *dev, struct usb_phy_generic *nop)return -EPROBE_DEFER ; } - nop->vbus_draw =devm_regulator_get_exclusive (dev,"vbus" ); -if (PTR_ERR (nop->vbus_draw) == -ENODEV ) - nop->vbus_draw =NULL ; -if (IS_ERR (nop->vbus_draw)) -return dev_err_probe (dev,PTR_ERR (nop->vbus_draw), -"could not get vbus regulator\n" ); - nop->dev = dev; nop->phy.dev = nop->dev; nop->phy.label ="nop-xceiv" ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 224/294 udp: do not accept non-tunnel GSO skbs landing in a tunnel
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Antoine Tenart <[email protected]>
[ Upstream commit 3d010c8031e39f5fa1e8b13ada77e0321091011f ]
When rx-udp-gro-forwarding is enabled UDP packets might be GROed when being forwarded. If such packets might land in a tunnel this can cause various issues and udp_gro_receive makes sure this isn't the case by looking for a matching socket. This is performed in udp4/6_gro_lookup_skb but only in the current netns. This is an issue with tunneled packets when the endpoint is in another netns. In such cases the packets will be GROed at the UDP level, which leads to various issues later on. The same thing can happen with rx-gro-list.
We saw this with geneve packets being GROed at the UDP level. In such case gso_size is set; later the packet goes through the geneve rx path, the geneve header is pulled, the offset are adjusted and frag_list skbs are not adjusted with regard to geneve. When those skbs hit skb_fragment, it will misbehave. Different outcomes are possible depending on what the GROed skbs look like; from corrupted packets to kernel crashes.
One example is a BUG_ON[1] triggered in skb_segment while processing the frag_list. Because gso_size is wrong (geneve header was pulled) skb_segment thinks there is "geneve header size" of data in frag_list, although it's in fact the next packet. The BUG_ON itself has nothing to do with the issue. This is only one of the potential issues.
Looking up for a matching socket in udp_gro_receive is fragile: the lookup could be extended to all netns (not speaking about performances) but nothing prevents those packets from being modified in between and we could still not find a matching socket. It's OK to keep the current logic there as it should cover most cases but we also need to make sure we handle tunnel packets being GROed too early.
This is done by extending the checks in udp_unexpected_gso: GSO packets lacking the SKB_GSO_UDP_TUNNEL/_CSUM bits and landing in a tunnel must be segmented.
[1] kernel BUG at net/core/skbuff.c:4408!
RIP: 0010:skb_segment+0xd2a/0xf70
__udp_gso_segment+0xaa/0x560--- include/linux/udp.h | 28 ++++++++++++++++++++++++++++ net/ipv4/udp.c | 7 +++++++ net/ipv4/udp_offload.c | 5 +++++ net/ipv6/udp.c | 2 +- 4 files changed, 41 insertions(+), 1 deletion(-)
include/linux/udp.h +28 -0
@@ -131,6 +131,24 @@ static inline void udp_cmsg_recv(struct msghdr *msg, struct sock *sk, } } +DECLARE_STATIC_KEY_FALSE (udp_encap_needed_key); +#if IS_ENABLED (CONFIG_IPV6 ) +DECLARE_STATIC_KEY_FALSE (udpv6_encap_needed_key); +#endif + +static inline bool udp_encap_needed (void ) +{ +if (static_branch_unlikely (&udp_encap_needed_key)) +return true; + +#if IS_ENABLED (CONFIG_IPV6 ) +if (static_branch_unlikely (&udpv6_encap_needed_key)) +return true; +#endif + +return false; +} +static inline bool udp_unexpected_gso (struct sock *sk,struct sk_buff *skb) {if (!skb_is_gso (skb))
@@ -142,6 +160,16 @@ static inline bool udp_unexpected_gso(struct sock *sk, struct sk_buff *skb)if (skb_shinfo (skb)->gso_type &SKB_GSO_FRAGLIST && !udp_sk (sk)->accept_udp_fraglist)return true; +/* GSO packets lacking the SKB_GSO_UDP_TUNNEL/_CSUM bits might still +* land in a tunnel as the socket check in udp_gro_receive cannot be +* foolproof. +*/ +if (udp_encap_needed () && +READ_ONCE (udp_sk (sk)->encap_rcv) && + !(skb_shinfo (skb)->gso_type & + (SKB_GSO_UDP_TUNNEL |SKB_GSO_UDP_TUNNEL_CSUM ))) +return true; +return false; }
net/ipv4/udp.c +7 -0
@@ -602,6 +602,13 @@ static inline bool __udp_is_mcast_sock(struct net *net, struct sock *sk, }DEFINE_STATIC_KEY_FALSE (udp_encap_needed_key); +EXPORT_SYMBOL (udp_encap_needed_key); + +#if IS_ENABLED (CONFIG_IPV6 ) +DEFINE_STATIC_KEY_FALSE (udpv6_encap_needed_key); +EXPORT_SYMBOL (udpv6_encap_needed_key); +#endif +void udp_encap_enable (void ) {static_branch_inc (&udp_encap_needed_key);
net/ipv4/udp_offload.c +5 -0
@@ -512,6 +512,11 @@ struct sk_buff *udp_gro_receive(struct list_head *head, struct sk_buff *skb,unsigned int off =skb_gro_offset (skb);int flush =1 ; +/* We can do L4 aggregation only if the packet can't land in a tunnel +* otherwise we could corrupt the inner stream. Detecting such packets +* cannot be foolproof and the aggregation might still happen in some +* cases. Such packets should be caught in udp_unexpected_gso later. +*/ NAPI_GRO_CB (skb)->is_flist =0 ;if (skb->dev->features &NETIF_F_GRO_FRAGLIST )NAPI_GRO_CB (skb)->is_flist = sk ? !udp_sk (sk)->gro_enabled:1 ;
net/ipv6/udp.c +1 -1
@@ -474,7 +474,7 @@ int udpv6_recvmsg(struct sock *sk, struct msghdr *msg, size_t len, goto try_again; } -DEFINE_STATIC_KEY_FALSE (udpv6_encap_needed_key); +DECLARE_STATIC_KEY_FALSE (udpv6_encap_needed_key);void udpv6_encap_enable (void ) {static_branch_inc (&udpv6_encap_needed_key);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 225/294 net: ravb: Always process TX descriptor ring
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Paul Barker <[email protected]>
[ Upstream commit 596a4254915f94c927217fe09c33a6828f33fb25 ]
The TX queue should be serviced each time the poll function is called, even if the full RX work budget has been consumed. This prevents starvation of the TX queue when RX bandwidth usage is high.
--- drivers/net/ethernet/renesas/ravb_main.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
drivers/net/ethernet/renesas/ravb_main.c +5 -2
@@ -911,12 +911,12 @@ static int ravb_poll(struct napi_struct *napi, int budget)int q = napi - priv->napi;int mask =BIT (q);int quota = budget; +bool unmask;/* Processing RX Descriptor Ring */ /* Clear RX interrupt */ ravb_write (ndev, ~(mask |RIS0_RESERVED ),RIS0 ); -if (ravb_rx (ndev, "a, q)) - goto out; + unmask = !ravb_rx (ndev, "a, q);/* Processing RX Descriptor Ring */ spin_lock_irqsave (&priv->lock, flags);
@@ -926,6 +926,9 @@ static int ravb_poll(struct napi_struct *napi, int budget)netif_wake_subqueue (ndev, q);spin_unlock_irqrestore (&priv->lock, flags); +if (!unmask) + goto out; +napi_complete (napi);/* Re-enable RX/TX interrupts */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 226/294 arm64: dts: qcom: sc7180: Remove clock for bluetooth on Trogdor
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Venkata Lakshmi Narayana Gubba <[email protected]>
[ Upstream commit a307a9773420dc7d385991f61fbede2fe100bd78 ]
Removed voting for RPMH_RF_CLK2 which is not required as it is getting managed by BT SoC through SW_CTRL line.
Stable-dep-of: e12e28009e58 ("arm64: dts: qcom: sc7180-trogdor: mark bluetooth address as broken")
--- arch/arm64/boot/dts/qcom/sc7180-trogdor.dtsi | 1 - 1 file changed, 1 deletion(-)
arch/arm64/boot/dts/qcom/sc7180-trogdor.dtsi +0 -1
@@ -810,7 +810,6 @@ ap_spi_fp: &spi10 { vddrf-supply = <&pp1300_l2c>; vddch0-supply = <&pp3300_l10c>; max-speed = <3200000>; - clocks = <&rpmhcc RPMH_RF_CLK2>; }; };
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 227/294 arm64: dts: qcom: sc7180-trogdor: mark bluetooth address as broken
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johan Hovold <[email protected]>
[ Upstream commit e12e28009e584c8f8363439f6a928ec86278a106 ]
Several Qualcomm Bluetooth controllers lack persistent storage for the device address and instead one can be provided by the boot firmware using the 'local-bd-address' devicetree property.
The Bluetooth bindings clearly states that the address should be specified in little-endian order, but due to a long-standing bug in the Qualcomm driver which reversed the address some boot firmware has been providing the address in big-endian order instead.
The boot firmware in SC7180 Trogdor Chromebooks is known to be affected so mark the 'local-bd-address' property as broken to maintain backwards compatibility with older firmware when fixing the underlying driver bug.
Note that ChromeOS always updates the kernel and devicetree in lockstep so that there is no need to handle backwards compatibility with older devicetrees.
--- arch/arm64/boot/dts/qcom/sc7180-trogdor.dtsi | 2 ++ 1 file changed, 2 insertions(+)
arch/arm64/boot/dts/qcom/sc7180-trogdor.dtsi +2 -0
@@ -810,6 +810,8 @@ ap_spi_fp: &spi10 { vddrf-supply = <&pp1300_l2c>; vddch0-supply = <&pp3300_l10c>; max-speed = <3200000>; + + qcom,local-bd-address-broken; }; };
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 228/294 ASoC: ops: Fix wraparound for mask in snd_soc_get_volsw
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Stephen Lee <[email protected]>
[ Upstream commit fc563aa900659a850e2ada4af26b9d7a3de6c591 ]
In snd_soc_info_volsw(), mask is generated by figuring out the index of the most significant bit set in max and converting the index to a bitmask through bit shift 1. Unintended wraparound occurs when max is an integer value with msb bit set. Since the bit shift value 1 is treated as an integer type, the left shift operation will wraparound and set mask to 0 instead of all 1's. In order to fix this, we type cast 1 as 1ULL to prevent the wraparound.
--- sound/soc/soc-ops.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
sound/soc/soc-ops.c +1 -1
@@ -246,7 +246,7 @@ int snd_soc_get_volsw(struct snd_kcontrol *kcontrol,int max = mc->max;int min = mc->min;int sign_bit = mc->sign_bit; -unsigned int mask = (1 <<fls (max)) -1 ; +unsigned int mask = (1ULL <<fls (max)) -1 ;unsigned int invert = mc->invert;int val;int ret;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 229/294 ata: sata_sx4: fix pdc20621_get_from_dimm() on 64-bit
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
[ Upstream commit 52f80bb181a9a1530ade30bc18991900bbb9697f ]
gcc warns about a memcpy() with overlapping pointers because of an incorrect size calculation:
In file included from include/linux/string.h:369,
from drivers/ata/sata_sx4.c:66:
In function 'memcpy_fromio',
inlined from 'pdc20621_get_from_dimm.constprop' at drivers/ata/sata_sx4.c:962:2:
include/linux/fortify-string.h:97:33: error: '__builtin_memcpy' accessing 4294934464 bytes at offsets 0 and [16, 16400] overlaps 6442385281 bytes at offset -2147450817 [-Werror=restrict]
97 | #define __underlying_memcpy __builtin_memcpy
| ^
include/linux/fortify-string.h:620:9: note: in expansion of macro '__underlying_memcpy'
620 | __underlying_##op(p, q, __fortify_size); \
| ^~~~~~~~~~~~~
include/linux/fortify-string.h:665:26: note: in expansion of macro '__fortify_memcpy_chk'
665 | #define memcpy(p, q, s) __fortify_memcpy_chk(p, q, s, \
| ^~~~~~~~~~~~~~~~~~~~
include/asm-generic/io.h:1184:9: note: in expansion of macro 'memcpy'
1184 | memcpy(buffer, __io_virt(addr), size);
| ^~~~~~The problem here is the overflow of an unsigned 32-bit number to a negative that gets converted into a signed 'long', keeping a large positive number.
Replace the complex calculation with a more readable min() variant that avoids the warning.
--- drivers/ata/sata_sx4.c | 6 ++---- 1 file changed, 2 insertions(+), 4 deletions(-)
drivers/ata/sata_sx4.c +2 -4
@@ -1004,8 +1004,7 @@ static void pdc20621_get_from_dimm(struct ata_host *host, void *psource, offset -= (idx * window_size); idx++; - dist = ((long ) (window_size - (offset + size))) >=0 ? size : - (long ) (window_size - offset); + dist =min (size, window_size - offset);memcpy_fromio (psource, dimm_mmio + offset /4 , dist); psource += dist;
@@ -1053,8 +1052,7 @@ static void pdc20621_put_to_dimm(struct ata_host *host, void *psource,readl (mmio +PDC_DIMM_WINDOW_CTLR ); offset -= (idx * window_size); idx++; - dist = ((long )(s32)(window_size - (offset + size))) >=0 ? size : - (long ) (window_size - offset); + dist =min (size, window_size - offset);memcpy_toio (dimm_mmio + offset /4 , psource, dist);writel (0x01 , mmio +PDC_GENERAL_CTLR );readl (mmio +PDC_GENERAL_CTLR );
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 230/294 scsi: mylex: Fix sysfs buffer lengths
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
[ Upstream commit 1197c5b2099f716b3de327437fb50900a0b936c9 ]
The myrb and myrs drivers use an odd way of implementing their sysfs files, calling snprintf() with a fixed length of 32 bytes to print into a page sized buffer. One of the strings is actually longer than 32 bytes, which clang can warn about:
drivers/scsi/myrb.c:1906:10: error: 'snprintf' will always be truncated; specified size is 32, but format string expands to at least 34 [-Werror,-Wformat-truncation] drivers/scsi/myrs.c:1089:10: error: 'snprintf' will always be truncated; specified size is 32, but format string expands to at least 34 [-Werror,-Wformat-truncation]
These could all be plain sprintf() without a length as the buffer is always long enough. On the other hand, sysfs files should not be overly long either, so just double the length to make sure the longest strings don't get truncated here.
--- drivers/scsi/myrb.c | 20 ++++++++++---------- drivers/scsi/myrs.c | 24 ++++++++++++------------ 2 files changed, 22 insertions(+), 22 deletions(-)
drivers/scsi/myrb.c +10 -10
@@ -1803,9 +1803,9 @@ static ssize_t raid_state_show(struct device *dev, name =myrb_devstate_name (ldev_info->state);if (name) - ret =snprintf (buf,32 ,"%s\n" , name); + ret =snprintf (buf,64 ,"%s\n" , name);else - ret =snprintf (buf,32 ,"Invalid (%02X)\n" , + ret =snprintf (buf,64 ,"Invalid (%02X)\n" , ldev_info->state); }else {struct myrb_pdev_state *pdev_info = sdev->hostdata;
@@ -1824,9 +1824,9 @@ static ssize_t raid_state_show(struct device *dev,else name =myrb_devstate_name (pdev_info->state);if (name) - ret =snprintf (buf,32 ,"%s\n" , name); + ret =snprintf (buf,64 ,"%s\n" , name);else - ret =snprintf (buf,32 ,"Invalid (%02X)\n" , + ret =snprintf (buf,64 ,"Invalid (%02X)\n" , pdev_info->state); }return ret;
@@ -1914,11 +1914,11 @@ static ssize_t raid_level_show(struct device *dev, name =myrb_raidlevel_name (ldev_info->raid_level);if (!name) -return snprintf (buf,32 ,"Invalid (%02X)\n" , +return snprintf (buf,64 ,"Invalid (%02X)\n" , ldev_info->state); -return snprintf (buf,32 ,"%s\n" , name); +return snprintf (buf,64 ,"%s\n" , name); } -return snprintf (buf,32 ,"Physical Drive\n" ); +return snprintf (buf,64 ,"Physical Drive\n" ); }static DEVICE_ATTR_RO (raid_level);
@@ -1931,15 +1931,15 @@ static ssize_t rebuild_show(struct device *dev,unsigned char status;if (sdev->channel <myrb_logical_channel (sdev->host)) -return snprintf (buf,32 ,"physical device - not rebuilding\n" ); +return snprintf (buf,64 ,"physical device - not rebuilding\n" ); status =myrb_get_rbld_progress (cb, &rbld_buf);if (rbld_buf.ldev_num != sdev->id || status !=MYRB_STATUS_SUCCESS ) -return snprintf (buf,32 ,"not rebuilding\n" ); +return snprintf (buf,64 ,"not rebuilding\n" ); -return snprintf (buf,32 ,"rebuilding block %u of %u\n" , +return snprintf (buf,64 ,"rebuilding block %u of %u\n" , rbld_buf.ldev_size - rbld_buf.blocks_left, rbld_buf.ldev_size); }
drivers/scsi/myrs.c +12 -12
@@ -950,9 +950,9 @@ static ssize_t raid_state_show(struct device *dev, name =myrs_devstate_name (ldev_info->dev_state);if (name) - ret =snprintf (buf,32 ,"%s\n" , name); + ret =snprintf (buf,64 ,"%s\n" , name);else - ret =snprintf (buf,32 ,"Invalid (%02X)\n" , + ret =snprintf (buf,64 ,"Invalid (%02X)\n" , ldev_info->dev_state); }else {struct myrs_pdev_info *pdev_info;
@@ -961,9 +961,9 @@ static ssize_t raid_state_show(struct device *dev, pdev_info = sdev->hostdata; name =myrs_devstate_name (pdev_info->dev_state);if (name) - ret =snprintf (buf,32 ,"%s\n" , name); + ret =snprintf (buf,64 ,"%s\n" , name);else - ret =snprintf (buf,32 ,"Invalid (%02X)\n" , + ret =snprintf (buf,64 ,"Invalid (%02X)\n" , pdev_info->dev_state); }return ret;
@@ -1069,13 +1069,13 @@ static ssize_t raid_level_show(struct device *dev, ldev_info = sdev->hostdata; name =myrs_raid_level_name (ldev_info->raid_level);if (!name) -return snprintf (buf,32 ,"Invalid (%02X)\n" , +return snprintf (buf,64 ,"Invalid (%02X)\n" , ldev_info->dev_state); }else name =myrs_raid_level_name (MYRS_RAID_PHYSICAL ); -return snprintf (buf,32 ,"%s\n" , name); +return snprintf (buf,64 ,"%s\n" , name); }static DEVICE_ATTR_RO (raid_level);
@@ -1089,7 +1089,7 @@ static ssize_t rebuild_show(struct device *dev,unsigned char status;if (sdev->channel < cs->ctlr_info->physchan_present) -return snprintf (buf,32 ,"physical device - not rebuilding\n" ); +return snprintf (buf,64 ,"physical device - not rebuilding\n" ); ldev_info = sdev->hostdata; ldev_num = ldev_info->ldev_num;
@@ -1101,11 +1101,11 @@ static ssize_t rebuild_show(struct device *dev,return -EIO ; }if (ldev_info->rbld_active) { -return snprintf (buf,32 ,"rebuilding block %zu of %zu\n" , +return snprintf (buf,64 ,"rebuilding block %zu of %zu\n" , (size_t )ldev_info->rbld_lba, (size_t )ldev_info->cfg_devsize); }else -return snprintf (buf,32 ,"not rebuilding\n" ); +return snprintf (buf,64 ,"not rebuilding\n" ); } static ssize_t rebuild_store(struct device *dev,
@@ -1194,7 +1194,7 @@ static ssize_t consistency_check_show(struct device *dev,unsigned char status;if (sdev->channel < cs->ctlr_info->physchan_present) -return snprintf (buf,32 ,"physical device - not checking\n" ); +return snprintf (buf,64 ,"physical device - not checking\n" ); ldev_info = sdev->hostdata;if (!ldev_info)
@@ -1202,11 +1202,11 @@ static ssize_t consistency_check_show(struct device *dev, ldev_num = ldev_info->ldev_num; status =myrs_get_ldev_info (cs, ldev_num, ldev_info);if (ldev_info->cc_active) -return snprintf (buf,32 ,"checking block %zu of %zu\n" , +return snprintf (buf,64 ,"checking block %zu of %zu\n" , (size_t )ldev_info->cc_lba, (size_t )ldev_info->cfg_devsize);else -return snprintf (buf,32 ,"not checking\n" ); +return snprintf (buf,64 ,"not checking\n" ); } static ssize_t consistency_check_store(struct device *dev,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 231/294 ata: sata_mv: Fix PCI device ID table declaration compilation warning
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
[ Upstream commit 3137b83a90646917c90951d66489db466b4ae106 ]
Building with W=1 shows a warning for an unused variable when CONFIG_PCI is diabled:
drivers/ata/sata_mv.c:790:35: error: unused variable 'mv_pci_tbl' [-Werror,-Wunused-const-variable] static const struct pci_device_id mv_pci_tbl[] = {
Move the table into the same block that containsn the pci_driver definition.
--- drivers/ata/sata_mv.c | 63 +++++++++++++++++++++---------------------- 1 file changed, 31 insertions(+), 32 deletions(-)
drivers/ata/sata_mv.c +31 -32
@@ -783,37 +783,6 @@ static const struct ata_port_info mv_port_info[] = { }, }; -static const struct pci_device_id mv_pci_tbl[] = { - {PCI_VDEVICE (MARVELL ,0x5040 ), chip_504x }, - {PCI_VDEVICE (MARVELL ,0x5041 ), chip_504x }, - {PCI_VDEVICE (MARVELL ,0x5080 ), chip_5080 }, - {PCI_VDEVICE (MARVELL ,0x5081 ), chip_508x }, -/* RocketRAID 1720/174x have different identifiers */ - {PCI_VDEVICE (TTI ,0x1720 ), chip_6042 }, - {PCI_VDEVICE (TTI ,0x1740 ), chip_6042 }, - {PCI_VDEVICE (TTI ,0x1742 ), chip_6042 }, - - {PCI_VDEVICE (MARVELL ,0x6040 ), chip_604x }, - {PCI_VDEVICE (MARVELL ,0x6041 ), chip_604x }, - {PCI_VDEVICE (MARVELL ,0x6042 ), chip_6042 }, - {PCI_VDEVICE (MARVELL ,0x6080 ), chip_608x }, - {PCI_VDEVICE (MARVELL ,0x6081 ), chip_608x }, - - {PCI_VDEVICE (ADAPTEC2 ,0x0241 ), chip_604x }, - -/* Adaptec 1430SA */ - {PCI_VDEVICE (ADAPTEC2 ,0x0243 ), chip_7042 }, - -/* Marvell 7042 support */ - {PCI_VDEVICE (MARVELL ,0x7042 ), chip_7042 }, - -/* Highpoint RocketRAID PCIe series */ - {PCI_VDEVICE (TTI ,0x2300 ), chip_7042 }, - {PCI_VDEVICE (TTI ,0x2310 ), chip_7042 }, - - { }/* terminate list */ -}; -static const struct mv_hw_ops mv5xxx_ops = { .phy_errata = mv5_phy_errata, .enable_leds = mv5_enable_leds,
@@ -4307,6 +4276,36 @@ static int mv_pci_init_one(struct pci_dev *pdev,static int mv_pci_device_resume (struct pci_dev *pdev);#endif +static const struct pci_device_id mv_pci_tbl[] = { + {PCI_VDEVICE (MARVELL ,0x5040 ), chip_504x }, + {PCI_VDEVICE (MARVELL ,0x5041 ), chip_504x }, + {PCI_VDEVICE (MARVELL ,0x5080 ), chip_5080 }, + {PCI_VDEVICE (MARVELL ,0x5081 ), chip_508x }, +/* RocketRAID 1720/174x have different identifiers */ + {PCI_VDEVICE (TTI ,0x1720 ), chip_6042 }, + {PCI_VDEVICE (TTI ,0x1740 ), chip_6042 }, + {PCI_VDEVICE (TTI ,0x1742 ), chip_6042 }, + + {PCI_VDEVICE (MARVELL ,0x6040 ), chip_604x }, + {PCI_VDEVICE (MARVELL ,0x6041 ), chip_604x }, + {PCI_VDEVICE (MARVELL ,0x6042 ), chip_6042 }, + {PCI_VDEVICE (MARVELL ,0x6080 ), chip_608x }, + {PCI_VDEVICE (MARVELL ,0x6081 ), chip_608x }, + + {PCI_VDEVICE (ADAPTEC2 ,0x0241 ), chip_604x }, + +/* Adaptec 1430SA */ + {PCI_VDEVICE (ADAPTEC2 ,0x0243 ), chip_7042 }, + +/* Marvell 7042 support */ + {PCI_VDEVICE (MARVELL ,0x7042 ), chip_7042 }, + +/* Highpoint RocketRAID PCIe series */ + {PCI_VDEVICE (TTI ,0x2300 ), chip_7042 }, + {PCI_VDEVICE (TTI ,0x2310 ), chip_7042 }, + + { }/* terminate list */ +};static struct pci_driver mv_pci_driver = { .name =DRV_NAME ,
@@ -4319,6 +4318,7 @@ static struct pci_driver mv_pci_driver = {#endif }; +MODULE_DEVICE_TABLE (pci, mv_pci_tbl);/** * mv_print_info - Dump key info to kernel log for perusal.
@@ -4491,7 +4491,6 @@ static void __exit mv_exit(void)MODULE_AUTHOR ("Brett Russ" );MODULE_DESCRIPTION ("SCSI low-level driver for Marvell SATA controllers" );MODULE_LICENSE ("GPL v2" ); -MODULE_DEVICE_TABLE (pci, mv_pci_tbl);MODULE_VERSION (DRV_VERSION );MODULE_ALIAS ("platform:" DRV_NAME );
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 232/294 ALSA: hda/realtek: Update Panasonic CF-SZ6 quirk to support headset with microphone
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: I Gede Agastya Darma Laksana <[email protected]>
commit 1576f263ee2147dc395531476881058609ad3d38 upstream.
This patch addresses an issue with the Panasonic CF-SZ6's existing quirk, specifically its headset microphone functionality. Previously, the quirk used ALC269_FIXUP_HEADSET_MODE, which does not support the CF-SZ6's design of a single 3.5mm jack for both mic and audio output effectively. The device uses pin 0x19 for the headset mic without jack detection.
Following verification on the CF-SZ6 and discussions with the original patch author, i determined that the update to ALC269_FIXUP_ASPIRE_HEADSET_MIC is the appropriate solution. This change is custom-designed for the CF-SZ6's unique hardware setup, which includes a single 3.5mm jack for both mic and audio output, connecting the headset microphone to pin 0x19 without the use of jack detection.
Message-ID: <[email protected]>
--- sound/pci/hda/patch_realtek.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
sound/pci/hda/patch_realtek.c +1 -1
@@ -9192,7 +9192,7 @@ static const struct snd_pci_quirk alc269SND_PCI_QUIRK (0x10ec ,0x124c ,"Intel Reference board" ,ALC295_FIXUP_CHROME_BOOK ),SND_PCI_QUIRK (0x10ec ,0x1252 ,"Intel Reference board" ,ALC295_FIXUP_CHROME_BOOK ),SND_PCI_QUIRK (0x10ec ,0x1254 ,"Intel Reference board" ,ALC295_FIXUP_CHROME_BOOK ), -SND_PCI_QUIRK (0x10f7 ,0x8338 ,"Panasonic CF-SZ6" ,ALC269_FIXUP_HEADSET_MODE ), +SND_PCI_QUIRK (0x10f7 ,0x8338 ,"Panasonic CF-SZ6" ,ALC269_FIXUP_ASPIRE_HEADSET_MIC ),SND_PCI_QUIRK (0x144d ,0xc109 ,"Samsung Ativ book 9 (NP900X3G)" ,ALC269_FIXUP_INV_DMIC ),SND_PCI_QUIRK (0x144d ,0xc169 ,"Samsung Notebook 9 Pen (NP930SBE-K01US)" ,ALC298_FIXUP_SAMSUNG_AMP ), SND_PCI_QUIRK(0x144d, 0xc176, "Samsung Notebook 9 Pro (NP930MBE-K04US)", ALC298_FIXUP_SAMSUNG_AMP),
Greg Kroah-Hartman
maintainerPATCH 233/294 driver core: Introduce device_link_wait_removal()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Herve Codina <[email protected]>
commit 0462c56c290a99a7f03e817ae5b843116dfb575c upstream.
The commit 80dd33cf72d1 ("drivers: base: Fix device link removal") introduces a workqueue to release the consumer and supplier devices used in the devlink.
In the job queued, devices are release and in turn, when all the references to these devices are dropped, the release function of the device itself is called.
Nothing is present to provide some synchronisation with this workqueue in order to ensure that all ongoing releasing operations are done and so, some other operations can be started safely.
For instance, in the following sequence:
1) of_platform_depopulate()
2) of_overlay_remove()
During the step 1, devices are released and related devlinks are removed (jobs pushed in the workqueue).
During the step 2, OF nodes are destroyed but, without any synchronisation with devlink removal jobs, of_overlay_remove() can raise warnings related to missing of_node_put():
ERROR: memory leak, expected refcount 1 instead of 2
Indeed, the missing of_node_put() call is going to be done, too late, from the workqueue job execution.
Introduce device_link_wait_removal() to offer a way to synchronize operations waiting for the end of devlink removals (i.e. end of workqueue jobs).
Also, as a flushing operation is done on the workqueue, the workqueue used is moved from a system-wide workqueue to a local one.
--- drivers/base/core.c | 26 +++++++++++++++++++++++--- include/linux/device.h | 1 + 2 files changed, 24 insertions(+), 3 deletions(-)
drivers/base/core.c +23 -3
@@ -53,6 +53,7 @@ static unsigned int defer_sync_state_coustatic unsigned int defer_fw_devlink_count;static LIST_HEAD (deferred_fw_devlink);static DEFINE_MUTEX (defer_fw_devlink_lock); +static struct workqueue_struct *device_link_wq;static bool fw_devlink_is_permissive (void );#ifdef CONFIG_SRCU
@@ -364,12 +365,26 @@ static void devlink_dev_release(struct d/* * It may take a while to complete this work because of the SRCU * synchronization in device_link_release_fn() and if the consumer or -* supplier devices get deleted when it runs, so put it into the "long" -* workqueue. +* supplier devices get deleted when it runs, so put it into the +* dedicated workqueue. */ -queue_work (system_long_wq, &link->rm_work); +queue_work (device_link_wq, &link->rm_work); } +/** +* device_link_wait_removal - Wait for ongoing devlink removal jobs to terminate +*/ +void device_link_wait_removal (void ) +{ +/* +* devlink removal jobs are queued in the dedicated work queue. +* To be sure that all removal jobs are terminated, ensure that any +* scheduled work has run to completion. +*/ +flush_workqueue (device_link_wq); +} +EXPORT_SYMBOL_GPL (device_link_wait_removal); +static struct class devlink_class = { .name ="devlink" , .owner =THIS_MODULE ,
@@ -3415,9 +3430,14 @@ int __init devices_init(void) sysfs_dev_char_kobj =kobject_create_and_add ("char" , dev_kobj);if (!sysfs_dev_char_kobj) goto char_kobj_err; + device_link_wq =alloc_workqueue ("device_link_wq" ,0 ,0 ); +if (!device_link_wq) + goto wq_err;return 0 ; + wq_err: +kobject_put (sysfs_dev_char_kobj); char_kobj_err:kobject_put (sysfs_dev_block_kobj); block_kobj_err:
include/linux/device.h +1 -0
@@ -973,6 +973,7 @@ void device_link_del(struct device_linkvoid device_link_remove (void *consumer,struct device *supplier);void device_links_supplier_sync_state_pause (void );void device_links_supplier_sync_state_resume (void ); +void device_link_wait_removal (void ); extern __printf(3, 4) int dev_err_probe(const struct device *dev, int err, const char *fmt, ...);
Greg Kroah-Hartman
maintainerPATCH 234/294 of: dynamic: Synchronize of_changeset_destroy() with the devlink removals
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Herve Codina <[email protected]>
commit 8917e7385346bd6584890ed362985c219fe6ae84 upstream.
In the following sequence:
1) of_platform_depopulate()
2) of_overlay_remove()
During the step 1, devices are destroyed and devlinks are removed. During the step 2, OF nodes are destroyed but __of_changeset_entry_destroy() can raise warnings related to missing of_node_put():
ERROR: memory leak, expected refcount 1 instead of 2 ...
Indeed, during the devlink removals performed at step 1, the removal itself releasing the device (and the attached of_node) is done by a job queued in a workqueue and so, it is done asynchronously with respect to function calls.
When the warning is present, of_node_put() will be called but wrongly too late from the workqueue job.
In order to be sure that any ongoing devlink removals are done before the of_node destruction, synchronize the of_changeset_destroy() with the devlink removals.
--- drivers/of/dynamic.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
drivers/of/dynamic.c +12 -0
@@ -9,6 +9,7 @@#define pr_fmt (fmt) "OF: " fmt +#include <linux/device.h> #include <linux/of.h> #include <linux/spinlock.h> #include <linux/slab.h>
@@ -675,6 +676,17 @@ void of_changeset_destroy(struct of_chan {struct of_changeset_entry *ce, *cen; +/* +* When a device is deleted, the device links to/from it are also queued +* for deletion. Until these device links are freed, the devices +* themselves aren't freed. If the device being deleted is due to an +* overlay change, this device might be holding a reference to a device +* node that will be freed. So, wait until all already pending device +* links are deleted before freeing a device node. This ensures we don't +* free any device node that has a non-zero reference count. +*/ +device_link_wait_removal (); +list_for_each_entry_safe_reverse (ce, cen, &ocs->entries, node)__of_changeset_entry_destroy (ce); }
Greg Kroah-Hartman
maintainerPATCH 235/294 x86/mce: Make sure to grab mce_sysfs_mutex in set_bank()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Borislav Petkov (AMD) <[email protected]>
commit 3ddf944b32f88741c303f0b21459dbb3872b8bc5 upstream.
Modifying a MCA bank's MCA_CTL bits which control which error types to be reported is done over
/sys/devices/system/machinecheck/
├── machinecheck0 │ ├── bank0 │ ├── bank1 │ ├── bank10 │ ├── bank11
...
sysfs nodes by writing the new bit mask of events to enable.
When the write is accepted, the kernel deletes all current timers and reinits all banks.
Doing that in parallel can lead to initializing a timer which is already armed and in the timer wheel, i.e., in use already:
ODEBUG: init active (active state 0) object: ffff888063a28000 object
type: timer_list hint: mce_timer_fn+0x0/0x240 arch/x86/kernel/cpu/mce/core.c:2642
WARNING: CPU: 0 PID: 8120 at lib/debugobjects.c:514 debug_print_object+0x1a0/0x2a0 lib/debugobjects.c:514
Fix that by grabbing the sysfs mutex as the rest of the MCA sysfs code does.
Reported by: Yue Sun <[email protected]>
Reported by: xingwei lee <[email protected]>
--- arch/x86/kernel/cpu/mce/core.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
arch/x86/kernel/cpu/mce/core.c +3 -1
@@ -2389,12 +2389,14 @@ static ssize_t set_bank(struct device *sreturn -EINVAL ; b = &per_cpu (mce_banks_array, s->id)[bank]; -if (!b->init)return -ENODEV ; b->ctl = new; + +mutex_lock (&mce_sysfs_mutex);mce_restart (); +mutex_unlock (&mce_sysfs_mutex);return size; }
Greg Kroah-Hartman
maintainerPATCH 236/294 s390/entry: align system call table on 8 bytes
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sumanth Korikkar <[email protected]>
commit 378ca2d2ad410a1cd5690d06b46c5e2297f4c8c0 upstream.
Align system call table on 8 bytes. With sys_call_table entry size of 8 bytes that eliminates the possibility of a system call pointer crossing cache line boundary.
--- arch/s390/kernel/entry.S | 1 + 1 file changed, 1 insertion(+)
arch/s390/kernel/entry.S +1 -0
@@ -1298,6 +1298,7 @@ ENDPROC(stack_overflow) #endif .section .rodata, "a" + .balign 8 #define SYSCALL(esame,emu) .quad __s390x_ ## esame .globl sys_call_table sys_call_table:
Greg Kroah-Hartman
maintainerPATCH 237/294 riscv: Fix spurious errors from __get/put_kernel_nofault
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Samuel Holland <[email protected]>
commit d080a08b06b6266cc3e0e86c5acfd80db937cb6b upstream.
These macros did not initialize __kr_err, so they could fail even if the access did not fault.
--- arch/riscv/include/asm/uaccess.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
arch/riscv/include/asm/uaccess.h +2 -2
@@ -468,7 +468,7 @@ unsigned long __must_check clear_user(vo#define __get_kernel_nofault (dst, src, type, err_label) \ do { \ - long __kr_err; \ + long __kr_err = 0; \ \ __get_user_nocheck(*((type *)(dst)), (type *)(src), __kr_err); \ if (unlikely(__kr_err)) \
@@ -477,7 +477,7 @@ do { \#define __put_kernel_nofault (dst, src, type, err_label) \ do { \ - long __kr_err; \ + long __kr_err = 0; \ \ __put_user_nocheck(*((type *)(src)), (type *)(dst), __kr_err); \ if (unlikely(__kr_err)) \
Greg Kroah-Hartman
maintainerPATCH 238/294 x86/bugs: Fix the SRSO mitigation on Zen3/4
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: "Borislav Petkov (AMD)" <[email protected]>
Commit 4535e1a4174c4111d92c5a9a21e542d232e0fcaa upstream.
The original version of the mitigation would patch in the calls to the untraining routines directly. That is, the alternative() in UNTRAIN_RET will patch in the CALL to srso_alias_untrain_ret() directly.
However, even if commit e7c25c441e9e ("x86/cpu: Cleanup the untrain mess") meant well in trying to clean up the situation, due to micro- architectural reasons, the untraining routine srso_alias_untrain_ret() must be the target of a CALL instruction and not of a JMP instruction as it is done now.
Reshuffle the alternative macros to accomplish that.
--- arch/x86/include/asm/asm-prototypes.h | 1 + arch/x86/include/asm/nospec-branch.h | 20 ++++++++++++++------ arch/x86/lib/retpoline.S | 4 +--- 3 files changed, 16 insertions(+), 9 deletions(-)
arch/x86/include/asm/asm-prototypes.h +1 -0
@@ -12,6 +12,7 @@#include <asm/special_insns.h> #include <asm/preempt.h> #include <asm/asm.h> +#include <asm/nospec-branch.h> #ifndef CONFIG_X86_CMPXCHG64 extern void cmpxchg8b_emu (void );
arch/x86/include/asm/nospec-branch.h +14 -6
@@ -155,11 +155,20 @@ .Lskip_rsb_\@: .endm +/* + * The CALL to srso_alias_untrain_ret() must be patched in directly at + * the spot where untraining must be done, ie., srso_alias_untrain_ret() + * must be the target of a CALL instruction instead of indirectly + * jumping to a wrapper which then calls it. Therefore, this macro is + * called outside of __UNTRAIN_RET below, for the time being, before the + * kernel can support nested alternatives with arbitrary nesting. + */ +.macro CALL_UNTRAIN_RET#ifdef CONFIG_CPU_UNRET_ENTRY -#define CALL_UNTRAIN_RET "call entry_untrain_ret" -#else -#define CALL_UNTRAIN_RET "" +ALTERNATIVE_2 "" ,"call entry_untrain_ret" ,X86_FEATURE_UNRET , \ +"call srso_alias_untrain_ret" ,X86_FEATURE_SRSO_ALIAS #endif +.endm/* * Mitigate RETBleed for AMD/Hygon Zen uarch. Requires KERNEL CR3 because the
@@ -176,9 +185,8 @@#if defined(CONFIG_CPU_UNRET_ENTRY ) || defined(CONFIG_CPU_IBPB_ENTRY ) || \ defined(CONFIG_CPU_SRSO )ANNOTATE_UNRET_END - ALTERNATIVE_2 "", \ -CALL_UNTRAIN_RET ,X86_FEATURE_UNRET , \ -"call entry_ibpb" ,X86_FEATURE_ENTRY_IBPB + CALL_UNTRAIN_RET +ALTERNATIVE "" ,"call entry_ibpb" ,X86_FEATURE_ENTRY_IBPB #endif .endm
arch/x86/lib/retpoline.S +1 -3
@@ -249,9 +249,7 @@ SYM_CODE_START(srso_return_thunk) SYM_CODE_END(srso_return_thunk) SYM_FUNC_START(entry_untrain_ret) - ALTERNATIVE_2 "jmp retbleed_untrain_ret", \ - "jmp srso_untrain_ret", X86_FEATURE_SRSO, \ - "jmp srso_alias_untrain_ret", X86_FEATURE_SRSO_ALIAS + ALTERNATIVE "jmp retbleed_untrain_ret", "jmp srso_untrain_ret", X86_FEATURE_SRSO SYM_FUNC_END(entry_untrain_ret) __EXPORT_THUNK(entry_untrain_ret)
Greg Kroah-Hartman
maintainerPATCH 239/294 x86/retpoline: Do the necessary fixup to the Zen3/4 srso return thunk for !SRSO
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: "Borislav Petkov (AMD)" <[email protected]>
Commit 0e110732473e14d6520e49d75d2c88ef7d46fe67 upstream.
The srso_alias_untrain_ret() dummy thunk in the !CONFIG_MITIGATION_SRSO case is there only for the altenative in CALL_UNTRAIN_RET to have a symbol to resolve.
However, testing with kernels which don't have CONFIG_MITIGATION_SRSO enabled, leads to the warning in patch_return() to fire:
missing return thunk: srso_alias_untrain_ret+0x0/0x10-0x0: eb 0e 66 66 2e
WARNING: CPU: 0 PID: 0 at arch/x86/kernel/alternative.c:826 apply_returns (arch/x86/kernel/alternative.c:826
Put in a plain "ret" there so that gcc doesn't put a return thunk in in its place which special and gets checked.
In addition:
ERROR: modpost: "srso_alias_untrain_ret" [arch/x86/kvm/kvm-amd.ko] undefined! make[2]: *** [scripts/Makefile.modpost:145: Module.symvers] Chyba 1 make[1]: *** [/usr/src/linux-6.8.3/Makefile:1873: modpost] Chyba 2
make: *** [Makefile:240: __sub-make] Chyba 2
since !SRSO builds would use the dummy return thunk as reported by [email protected], https://bugzilla.kernel.org/show_bug.cgi?id=218679.
--- arch/x86/lib/retpoline.S | 1 + 1 file changed, 1 insertion(+)
arch/x86/lib/retpoline.S +1 -0
@@ -108,6 +108,7 @@ SYM_START(srso_alias_untrain_ret, SYM_L_ ret int3 SYM_FUNC_END(srso_alias_untrain_ret) +__EXPORT_THUNK(srso_alias_untrain_ret) #endif SYM_START(srso_alias_safe_ret, SYM_L_GLOBAL, SYM_A_NONE)
Greg Kroah-Hartman
maintainerPATCH 240/294 mptcp: dont account accept() of non-MPC client as fallback to TCP
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Davide Caratti <[email protected]>
commit 7a1b3490f47e88ec4cbde65f1a77a0f4bc972282 upstream.
Current MPTCP servers increment MPTcpExtMPCapableFallbackACK when they accept non-MPC connections. As reported by Christoph, this is "surprising" because the counter might become greater than MPTcpExtMPCapableSYNRX.
MPTcpExtMPCapableFallbackACK counter's name suggests it should only be incremented when a connection was seen using MPTCP options, then a fallback to TCP has been done. Let's do that by incrementing it when the subflow context of an inbound MPC connection attempt is dropped. Also, update mptcp_connect.sh kselftest, to ensure that the above MIB does not increment in case a pure TCP client connects to a MPTCP server.
--- net/mptcp/protocol.c | 3 --- net/mptcp/subflow.c | 3 +++ 2 files changed, 3 insertions(+), 3 deletions(-)
net/mptcp/protocol.c +0 -3
@@ -2218,9 +2218,6 @@ static struct sock *mptcp_accept(struct__MPTCP_INC_STATS (sock_net (sk),MPTCP_MIB_MPCAPABLEPASSIVEACK );local_bh_enable (); - }else { -MPTCP_INC_STATS (sock_net (sk), -MPTCP_MIB_MPCAPABLEPASSIVEFALLBACK ); } out:
net/mptcp/subflow.c +3 -0
@@ -595,6 +595,9 @@ create_child:if (fallback_is_fatal) goto dispose_child; +if (fallback) +SUBFLOW_REQ_INC_STATS (req,MPTCP_MIB_MPCAPABLEPASSIVEFALLBACK ); +subflow_drop_ctx (child); goto out; }
Greg Kroah-Hartman
maintainerPATCH 241/294 x86/cpufeatures: Add CPUID_LNX_5 to track recently added Linux-defined word
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Sean Christopherson <[email protected]>
commit 8cb4a9a82b21623dbb4b3051dd30d98356cf95bc upstream.
Add CPUID_LNX_5 to track cpufeatures' word 21, and add the appropriate compile-time assert in KVM to prevent direct lookups on the features in CPUID_LNX_5. KVM uses X86_FEATURE_* flags to manage guest CPUID, and so must translate features that are scattered by Linux from the Linux-defined bit to the hardware-defined bit, i.e. should never try to directly access scattered features in guest CPUID.
Opportunistically add NR_CPUID_WORDS to enum cpuid_leafs, along with a compile-time assert in KVM's CPUID infrastructure to ensure that future additions update cpuid_leafs along with NCAPINTS.
No functional change intended.
--- arch/x86/include/asm/cpufeature.h | 2 ++ arch/x86/kvm/cpuid.h | 2 ++ 2 files changed, 4 insertions(+)
arch/x86/include/asm/cpufeature.h +2 -0
@@ -33,6 +33,8 @@ enum cpuid_leafsCPUID_7_EDX ,CPUID_8000_001F_EAX ,CPUID_8000_0021_EAX , +CPUID_LNX_5 , + NR_CPUID_WORDS, };#ifdef CONFIG_X86_FEATURE_NAMES
arch/x86/kvm/cpuid.h +2 -0
@@ -76,10 +76,12 @@ static const struct cpuid_reg reverse_cp*/ static __always_inline void reverse_cpuid_check(unsigned int x86_leaf) { +BUILD_BUG_ON (NR_CPUID_WORDS !=NCAPINTS );BUILD_BUG_ON (x86_leaf ==CPUID_LNX_1 );BUILD_BUG_ON (x86_leaf ==CPUID_LNX_2 );BUILD_BUG_ON (x86_leaf ==CPUID_LNX_3 );BUILD_BUG_ON (x86_leaf ==CPUID_LNX_4 ); +BUILD_BUG_ON (x86_leaf ==CPUID_LNX_5 );BUILD_BUG_ON (x86_leaf >=ARRAY_SIZE (reverse_cpuid));BUILD_BUG_ON (reverse_cpuid[x86_leaf].function ==0 ); }
Greg Kroah-Hartman
maintainerPATCH 242/294 objtool: Add asm version of STACK_FRAME_NON_STANDARD
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Josh Poimboeuf <[email protected]>
commit 081df94301e317e84c3413686043987da2c3e39d upstream.
To be used for adding asm functions to the ignore list. The "aw" is needed to help the ELF section metadata match GCC-created sections. Otherwise the linker creates duplicate sections instead of combining them.
--- include/linux/objtool.h | 8 ++++++++ tools/include/linux/objtool.h | 8 ++++++++ 2 files changed, 16 insertions(+)
include/linux/objtool.h +8 -0
@@ -141,6 +141,12 @@ struct unwind_hint { .popsection .endm +.macro STACK_FRAME_NON_STANDARD func:req + .pushsection .discard.func_stack_frame_non_standard,"aw" + .long \func - . + .popsection +.endm +#endif /* __ASSEMBLY__ */ #else /* !CONFIG_STACK_VALIDATION */
@@ -158,6 +164,8 @@ struct unwind_hint { .endm .macro ANNOTATE_NOENDBR .endm +.macro STACK_FRAME_NON_STANDARD func:req +.endm#endif #endif /* CONFIG_STACK_VALIDATION */
tools/include/linux/objtool.h +8 -0
@@ -141,6 +141,12 @@ struct unwind_hint { .popsection .endm +.macro STACK_FRAME_NON_STANDARD func:req + .pushsection .discard.func_stack_frame_non_standard,"aw" + .long \func - . + .popsection +.endm +#endif /* __ASSEMBLY__ */ #else /* !CONFIG_STACK_VALIDATION */
@@ -158,6 +164,8 @@ struct unwind_hint { .endm .macro ANNOTATE_NOENDBR .endm +.macro STACK_FRAME_NON_STANDARD func:req +.endm#endif #endif /* CONFIG_STACK_VALIDATION */
Greg Kroah-Hartman
maintainerPATCH 243/294 wifi: ath9k: fix LNA selection in ath_ant_try_scan()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dmitry Antipov <[email protected]>
[ Upstream commit d6b27eb997ef9a2aa51633b3111bc4a04748e6d3 ]
In 'ath_ant_try_scan()', (most likely) the 2nd LNA's signal strength should be used in comparison against RSSI when selecting first LNA as the main one. Compile tested only.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
--- drivers/net/wireless/ath/ath9k/antenna.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/net/wireless/ath/ath9k/antenna.c +1 -1
@@ -643,7 +643,7 @@ static void ath_ant_try_scan(struct ath_ant_comb *antcomb, conf->main_lna_conf =ATH_ANT_DIV_COMB_LNA1 ; conf->alt_lna_conf =ATH_ANT_DIV_COMB_LNA1_PLUS_LNA2 ; }else if (antcomb->rssi_sub > - antcomb->rssi_lna1) { + antcomb->rssi_lna2) {/* set to A-B */ conf->main_lna_conf =ATH_ANT_DIV_COMB_LNA1 ; conf->alt_lna_conf =ATH_ANT_DIV_COMB_LNA1_MINUS_LNA2 ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 244/294 batman-adv: Return directly after a failed batadv_dat_select_candidates() in batadv_dat_forward_data()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Markus Elfring <[email protected]>
[ Upstream commit ffc15626c861f811f9778914be004fcf43810a91 ]
The kfree() function was called in one case by
the batadv_dat_forward_data() function during error handling even if the passed variable contained a null pointer. This issue was detected by using the Coccinelle software.
* Thus return directly after a batadv_dat_select_candidates() call failed at the beginning.
* Delete the label “out” which became unnecessary with this refactoring.
--- net/batman-adv/distributed-arp-table.c | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-)
net/batman-adv/distributed-arp-table.c +1 -2
@@ -687,7 +687,7 @@ static bool batadv_dat_forward_data(struct batadv_priv *bat_priv, cand =batadv_dat_select_candidates (bat_priv, ip, vid);if (!cand) - goto out; +return ret;batadv_dbg (BATADV_DBG_DAT , bat_priv,"DHT_SEND for %pI4\n" , &ip);
@@ -731,7 +731,6 @@ static bool batadv_dat_forward_data(struct batadv_priv *bat_priv,batadv_orig_node_put (cand[i].orig_node); } -out:kfree (cand);return ret; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 245/294 batman-adv: Improve exception handling in batadv_throw_uevent()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Markus Elfring <[email protected]>
[ Upstream commit 5593e9abf1cf2bf096366d8c7fd933bc69d561ce ]
The kfree() function was called in up to three cases by the batadv_throw_uevent() function during error handling even if the passed variable contained a null pointer. This issue was detected by using the Coccinelle software.
* Thus adjust jump targets.
* Reorder kfree() calls at the end.
--- net/batman-adv/main.c | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-)
net/batman-adv/main.c +8 -6
@@ -732,29 +732,31 @@ int batadv_throw_uevent(struct batadv_priv *bat_priv, enum batadv_uev_type type,"%s%s" ,BATADV_UEV_TYPE_VAR , batadv_uev_type_str[type]);if (!uevent_env[0 ]) - goto out; + goto report_error; uevent_env[1 ] =kasprintf (GFP_ATOMIC ,"%s%s" ,BATADV_UEV_ACTION_VAR , batadv_uev_action_str[action]);if (!uevent_env[1 ]) - goto out; + goto free_first_env;/* If the event is DEL, ignore the data field */ if (action !=BATADV_UEV_DEL ) { uevent_env[2 ] =kasprintf (GFP_ATOMIC ,"%s%s" ,BATADV_UEV_DATA_VAR , data);if (!uevent_env[2 ]) - goto out; + goto free_second_env; } ret =kobject_uevent_env (bat_kobj,KOBJ_CHANGE , uevent_env); -out: -kfree (uevent_env[0 ]); -kfree (uevent_env[1 ]);kfree (uevent_env[2 ]); +free_second_env: +kfree (uevent_env[1 ]); +free_first_env: +kfree (uevent_env[0 ]);if (ret) +report_error: batadv_dbg(BATADV_DBG_BATMAN, bat_priv, "Impossible to send uevent for (%s,%s,%s) event (err: %d)\n", batadv_uev_type_str[type],
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 246/294 VMCI: Fix memcpy() run-time warning in dg_dispatch_as_host()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Harshit Mogalapalli <[email protected]>
[ Upstream commit 19b070fefd0d024af3daa7329cbc0d00de5302ec ]
Syzkaller hit 'WARNING in dg_dispatch_as_host' bug.
memcpy: detected field-spanning write (size 56) of single field "&dg_info->msg"
at drivers/misc/vmw_vmci/vmci_datagram.c:237 (size 24) WARNING: CPU: 0 PID: 1555 at drivers/misc/vmw_vmci/vmci_datagram.c:237 dg_dispatch_as_host+0x88e/0xa60 drivers/misc/vmw_vmci/vmci_datagram.c:237
Some code commentry, based on my understanding:
544 #define VMCI_DG_SIZE(_dg) (VMCI_DG_HEADERSIZE + (size_t)(_dg)->payload_size) /// This is 24 + payload_size
memcpy(&dg_info->msg, dg, dg_size); Destination = dg_info->msg ---> this is a 24 byte structure(struct vmci_datagram) Source = dg --> this is a 24 byte structure (struct vmci_datagram) Size = dg_size = 24 + payload_size
{payload_size = 56-24 =32} -- Syzkaller managed to set payload_size to 32.
35 struct delayed_datagram_info {
36 struct datagram_entry *entry; 37 struct work_struct work; 38 bool in_dg_host_queue; 39 /* msg and msg_payload must be together. */ 40 struct vmci_datagram msg; 41 u8 msg_payload[];
42 };
So those extra bytes of payload are copied into msg_payload[], a run time warning is seen while fuzzing with Syzkaller.
One possible way to fix the warning is to split the memcpy() into two parts -- one -- direct assignment of msg and second taking care of payload.
Gustavo quoted:
"Under FORTIFY_SOURCE we should not copy data across multiple members in a structure."
--- drivers/misc/vmw_vmci/vmci_datagram.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
drivers/misc/vmw_vmci/vmci_datagram.c +2 -1
@@ -234,7 +234,8 @@ static int dg_dispatch_as_host(u32 context_id, struct vmci_datagram *dg) dg_info->in_dg_host_queue = true; dg_info->entry = dst_entry; -memcpy (&dg_info->msg, dg, dg_size); + dg_info->msg = *dg; +memcpy (&dg_info->msg_payload, dg +1 , dg->payload_size);INIT_WORK (&dg_info->work, dg_delayed_dispatch);schedule_work (&dg_info->work);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 247/294 panic: Flush kernel log buffer at the end
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: John Ogness <[email protected]>
[ Upstream commit d988d9a9b9d180bfd5c1d353b3b176cb90d6861b ]
If the kernel crashes in a context where printk() calls always defer printing (such as in NMI or inside a printk_safe section) then the final panic messages will be deferred to irq_work. But if irq_work is not available, the messages will not get printed unless explicitly flushed. The result is that the final "end Kernel panic" banner does not get printed.
Add one final flush after the last printk() call to make sure the final panic messages make it out as well.
--- kernel/panic.c | 8 ++++++++ 1 file changed, 8 insertions(+)
kernel/panic.c +8 -0
@@ -427,6 +427,14 @@ void panic(const char *fmt, ...)/* Do not scroll important messages printed above */ suppress_printk =1 ; + +/* +* The final messages may not have been printed if in a context that +* defers printing (such as NMI) and irq_work is not available. +* Explicitly flush the kernel log buffer one last time. +*/ +console_flush_on_panic (CONSOLE_FLUSH_PENDING ); +local_irq_enable ();for (i =0 ; ; i +=PANIC_TIMER_STEP ) {touch_softlockup_watchdog ();
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 248/294 arm64: dts: rockchip: fix rk3328 hdmi ports node
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johan Jonker <[email protected]>
[ Upstream commit 1d00ba4700d1e0f88ae70d028d2e17e39078fa1c ]
Fix rk3328 hdmi ports node so that it matches the
rockchip,dw-hdmi.yaml binding.
--- arch/arm64/boot/dts/rockchip/rk3328.dtsi | 11 ++++++++++- 1 file changed, 10 insertions(+), 1 deletion(-)
arch/arm64/boot/dts/rockchip/rk3328.dtsi +10 -1
@@ -732,11 +732,20 @@ hdmi: hdmi@ff3c0000 { status = "disabled"; ports { - hdmi_in: port { + #address-cells = <1>; + #size-cells = <0>; + + hdmi_in: port@0 { + reg = <0>; + hdmi_in_vop: endpoint { remote-endpoint = <&vop_out_hdmi>; }; }; + + hdmi_out: port@1 { + reg = <1>; + }; }; };
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 249/294 arm64: dts: rockchip: fix rk3399 hdmi ports node
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Johan Jonker <[email protected]>
[ Upstream commit f051b6ace7ffcc48d6d1017191f167c0a85799f6 ]
Fix rk3399 hdmi ports node so that it matches the
rockchip,dw-hdmi.yaml binding.
--- arch/arm64/boot/dts/rockchip/rk3399.dtsi | 12 ++++++++++-- 1 file changed, 10 insertions(+), 2 deletions(-)
arch/arm64/boot/dts/rockchip/rk3399.dtsi +10 -2
@@ -1769,6 +1769,7 @@ simple-audio-card,codec { hdmi: hdmi@ff940000 { compatible = "rockchip,rk3399-dw-hdmi"; reg = <0x0 0xff940000 0x0 0x20000>; + reg-io-width = <4>; interrupts = <GIC_SPI 23 IRQ_TYPE_LEVEL_HIGH 0>; clocks = <&cru PCLK_HDMI_CTRL>, <&cru SCLK_HDMI_SFR>,
@@ -1777,13 +1778,16 @@ hdmi: hdmi@ff940000 { <&cru PLL_VPLL>; clock-names = "iahb", "isfr", "cec", "grf", "vpll"; power-domains = <&power RK3399_PD_HDCP>; - reg-io-width = <4>; rockchip,grf = <&grf>; #sound-dai-cells = <0>; status = "disabled"; ports { - hdmi_in: port { + #address-cells = <1>; + #size-cells = <0>; + + hdmi_in: port@0 { + reg = <0>; #address-cells = <1>; #size-cells = <0>;
@@ -1796,6 +1800,10 @@ hdmi_in_vopl: endpoint@1 { remote-endpoint = <&vopl_out_hdmi>; }; }; + + hdmi_out: port@1 { + reg = <1>; + }; }; };
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 250/294 ionic: set adminq irq affinity
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Shannon Nelson <[email protected]>
[ Upstream commit c699f35d658f3c21b69ed24e64b2ea26381e941d ]
We claim to have the AdminQ on our irq0 and thus cpu id 0, but we need to be sure we set the affinity hint to try to keep it there.
--- drivers/net/ethernet/pensando/ionic/ionic_lif.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
drivers/net/ethernet/pensando/ionic/ionic_lif.c +4 -1
@@ -2708,9 +2708,12 @@ static int ionic_lif_adminq_init(struct ionic_lif *lif)napi_enable (&qcq->napi); -if (qcq->flags &IONIC_QCQ_F_INTR ) +if (qcq->flags &IONIC_QCQ_F_INTR ) { +irq_set_affinity_hint (qcq->intr.vector, + &qcq->intr.affinity_mask);ionic_intr_mask (idev->intr_ctrl, qcq->intr.index,IONIC_INTR_MASK_CLEAR ); + } qcq->flags |=IONIC_QCQ_F_INITED ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 251/294 pstore/zone: Add a null pointer check to the psz_kmsg_read
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kunwu Chan <[email protected]>
[ Upstream commit 98bc7e26e14fbb26a6abf97603d59532475e97f8 ]
kasprintf() returns a pointer to dynamically allocated memory which can be NULL upon failure. Ensure the allocation was successful by checking the pointer validity.
--- fs/pstore/zone.c | 2 ++ 1 file changed, 2 insertions(+)
fs/pstore/zone.c +2 -0
@@ -973,6 +973,8 @@ static ssize_t psz_kmsg_read(struct pstore_zone *zone,char *buf =kasprintf (GFP_KERNEL ,"%s: Total %d times\n" ,kmsg_dump_reason_str (record->reason), record->count); +if (!buf) +return -ENOMEM ; hlen =strlen (buf); record->buf =krealloc (buf, hlen + size,GFP_KERNEL );if (!record->buf) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 252/294 tools/power x86_energy_perf_policy: Fix file leak in get_pkg_num()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Samasth Norway Ananda <[email protected]>
[ Upstream commit f85450f134f0b4ca7e042dc3dc89155656a2299d ]
In function get_pkg_num() if fopen_or_die() succeeds it returns a file pointer to be used. But fclose() is never called before returning from the function.
--- tools/power/x86/x86_energy_perf_policy/x86_energy_perf_policy.c | 1 + 1 file changed, 1 insertion(+)
tools/power/x86/x86_energy_perf_policy/x86_energy_perf_policy.c +1 -0
@@ -1152,6 +1152,7 @@ unsigned int get_pkg_num(int cpu) retval =fscanf (fp,"%d\n" , &pkg);if (retval !=1 )errx (1 ,"%s: failed to parse" , pathname); +fclose (fp);return pkg; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 253/294 btrfs: handle chunk tree lookup error in btrfs_relocate_sys_chunks()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: David Sterba <[email protected]>
[ Upstream commit 7411055db5ce64f836aaffd422396af0075fdc99 ]
The unhandled case in btrfs_relocate_sys_chunks() loop is a corruption, as it could be caused only by two impossible conditions:
- at first the search key is set up to look for a chunk tree item, with offset -1, this is an inexact search and the key->offset will contain the correct offset upon a successful search, a valid chunk tree item cannot have an offset -1
- after first successful search, the found_key corresponds to a chunk item, the offset is decremented by 1 before the next loop, it's impossible to find a chunk item there due to alignment and size constraints
--- fs/btrfs/volumes.c | 12 +++++++++++- 1 file changed, 11 insertions(+), 1 deletion(-)
fs/btrfs/volumes.c +11 -1
@@ -3178,7 +3178,17 @@ static int btrfs_relocate_sys_chunks(struct btrfs_fs_info *fs_info)mutex_unlock (&fs_info->delete_unused_bgs_mutex); goto error; } -BUG_ON (ret ==0 );/* Corruption */ +if (ret ==0 ) { +/* +* On the first search we would find chunk tree with +* offset -1, which is not possible. On subsequent +* loops this would find an existing item on an invalid +* offset (one less than the previous one, wrong +* alignment and size). +*/ + ret = -EUCLEAN ; + goto error; + } ret =btrfs_previous_item (chunk_root, path, key.objectid, key.type);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 254/294 btrfs: export: handle invalid inode or root reference in btrfs_get_parent()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: David Sterba <[email protected]>
[ Upstream commit 26b66d1d366a375745755ca7365f67110bbf6bd5 ]
The get_parent handler looks up a parent of a given dentry, this can be either a subvolume or a directory. The search is set up with offset -1 but it's never expected to find such item, as it would break allowed range of inode number or a root id. This means it's a corruption (ext4 also returns this error code).
--- fs/btrfs/export.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-)
fs/btrfs/export.c +8 -1
@@ -161,8 +161,15 @@ struct dentry *btrfs_get_parent(struct dentry *child) ret =btrfs_search_slot (NULL , root, &key, path,0 ,0 );if (ret <0 ) goto fail; +if (ret ==0 ) { +/* +* Key with offset of -1 found, there would have to exist an +* inode with such number or a root with such id. +*/ + ret = -EUCLEAN ; + goto fail; + } -BUG_ON (ret ==0 );/* Key with offset of -1 found */ if (path->slots[0 ] ==0 ) { ret = -ENOENT ; goto fail;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 255/294 btrfs: send: handle path ref underflow in header iterate_inode_ref()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: David Sterba <[email protected]>
[ Upstream commit 3c6ee34c6f9cd12802326da26631232a61743501 ]
Change BUG_ON to proper error handling if building the path buffer fails. The pointers are not printed so we don't accidentally leak kernel addresses.
--- fs/btrfs/send.c | 10 +++++++++- 1 file changed, 9 insertions(+), 1 deletion(-)
fs/btrfs/send.c +9 -1
@@ -966,7 +966,15 @@ static int iterate_inode_ref(struct btrfs_root *root, struct btrfs_path *path, ret =PTR_ERR (start); goto out; } -BUG_ON (start < p->buf); +if (unlikely (start < p->buf)) { +btrfs_err (root->fs_info, +"send: path ref buffer underflow for key (%llu %u %llu)" , + found_key->objectid, + found_key->type, + found_key->offset); + ret = -EINVAL ; + goto out; + } } p->start = start; }else {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 256/294 net/smc: reduce rtnl pressure in smc_pnet_create_pnetids_list()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Eric Dumazet <[email protected]>
[ Upstream commit 00af2aa93b76b1bade471ad0d0525d4d29ca5cc0 ]
Many syzbot reports show extreme rtnl pressure, and many of them hint that smc acquires rtnl in netns creation for no good reason [1]
This patch returns early from smc_pnet_net_init()
if there is no netdevice yet.
I am not even sure why smc_pnet_create_pnetids_list() even exists, because smc_pnet_netdev_event() is also calling smc_pnet_add_base_pnetid() when handling NETDEV_UP event.
[1] extract of typical syzbot reports
2 locks held by syz-executor.3/12252:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.4/12253:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.1/12257:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.2/12261:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.0/12265:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.3/12268:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.4/12271:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.1/12274:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
2 locks held by syz-executor.2/12280:
#0: ffffffff8f369610 (pernet_ops_rwsem){++++}-{3:3}, at: copy_net_ns+0x4c7/0x7b0 net/core/net_namespace.c:491 #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_create_pnetids_list net/smc/smc_pnet.c:809 [inline] #1: ffffffff8f375b88 (rtnl_mutex){+.+.}-{3:3}, at: smc_pnet_net_init+0x10a/0x1e0 net/smc/smc_pnet.c:878
--- net/smc/smc_pnet.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
net/smc/smc_pnet.c +10 -0
@@ -797,6 +797,16 @@ static void smc_pnet_create_pnetids_list(struct net *net)u8 ndev_pnetid[SMC_MAX_PNETID_LEN ];struct net_device *dev; +/* Newly created netns do not have devices. +* Do not even acquire rtnl. +*/ +if (list_empty (&net->dev_base_head)) +return ; + +/* Note: This might not be needed, because smc_pnet_netdev_event() +* is also calling smc_pnet_add_base_pnetid() when handling +* NETDEV_UP event. +*/ rtnl_lock ();for_each_netdev (net, dev)smc_pnet_add_base_pnetid (net, dev, ndev_pnetid);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 257/294 Bluetooth: btintel: Fix null ptr deref in btintel_read_version
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Edward Adam Davis <[email protected]>
[ Upstream commit b79e040910101b020931ba0c9a6b77e81ab7f645 ]
If hci_cmd_sync_complete() is triggered and skb is NULL, then hdev->req_skb is NULL, which will cause this issue.
--- drivers/bluetooth/btintel.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
drivers/bluetooth/btintel.c +1 -1
@@ -344,7 +344,7 @@ int btintel_read_version(struct hci_dev *hdev, struct intel_version *ver)struct sk_buff *skb; skb =__hci_cmd_sync (hdev,0xfc05 ,0 ,NULL ,HCI_CMD_TIMEOUT ); -if (IS_ERR (skb)) { +if (IS_ERR_OR_NULL (skb)) {bt_dev_err (hdev,"Reading Intel version information failed (%ld)" ,PTR_ERR (skb));return PTR_ERR (skb);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 258/294 Input: synaptics-rmi4 - fail probing if memory allocation for "phys" fails
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Kunwu Chan <[email protected]>
[ Upstream commit bc4996184d56cfaf56d3811ac2680c8a0e2af56e ]
While input core can work with input->phys set to NULL userspace might depend on it, so better fail probing if allocation fails. The system must be in a pretty bad shape for it to happen anyway.
--- drivers/input/rmi4/rmi_driver.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
drivers/input/rmi4/rmi_driver.c +5 -1
@@ -1196,7 +1196,11 @@ static int rmi_driver_probe(struct device *dev) }rmi_driver_set_input_params (rmi_dev, data->input); data->input->phys =devm_kasprintf (dev,GFP_KERNEL , -"%s/input0" ,dev_name (dev)); +"%s/input0" ,dev_name (dev)); +if (!data->input->phys) { + retval = -ENOMEM ; + goto err; + } } retval =rmi_init_functions (data);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 259/294 pinctrl: renesas: checker: Limit cfg reg enum checks to provided IDs
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Geert Uytterhoeven <[email protected]>
[ Upstream commit 3803584a4e9b65bb5b013f862f55c5055aa86c25 ]
If the number of provided enum IDs in a variable width config register description does not match the expected number, the checker uses the expected number for validating the individual enum IDs.
However, this may cause out-of-bounds accesses on the array holding the enum IDs, leading to bogus enum_id conflict warnings. Worse, if the bug is an incorrect bit field description (e.g. accidentally using "12" instead of "-12" for a reserved field), thousands of warnings may be printed, overflowing the kernel log buffer.
Fix this by limiting the enum ID check to the number of provided enum IDs.
--- drivers/pinctrl/renesas/core.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
drivers/pinctrl/renesas/core.c +3 -1
@@ -868,9 +868,11 @@ static void __init sh_pfc_check_cfg_reg(const char *drvname,sh_pfc_err ("reg 0x%x: var_field_width declares %u instead of %u bits\n" , cfg_reg->reg, rw, cfg_reg->reg_width); -if (n != cfg_reg->nr_enum_ids) +if (n != cfg_reg->nr_enum_ids) {sh_pfc_err ("reg 0x%x: enum_ids[] has %u instead of %u values\n" , cfg_reg->reg, cfg_reg->nr_enum_ids, n); + n = cfg_reg->nr_enum_ids; + } check_enum_ids:sh_pfc_check_reg_enums (drvname, cfg_reg->reg, cfg_reg->enum_ids, n);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 260/294 sysv: dont call sb_bread() with pointers_lock held
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Tetsuo Handa <[email protected]>
[ Upstream commit f123dc86388cb669c3d6322702dc441abc35c31e ]
syzbot is reporting sleep in atomic context in SysV filesystem [1], for sb_bread() is called with rw_spinlock held.
A "write_lock(&pointers_lock) => read_lock(&pointers_lock) deadlock" bug and a "sb_bread() with write_lock(&pointers_lock)" bug were introduced by "Replace BKL for chain locking with sysvfs-private rwlock" in Linux 2.5.12.
Then, "[PATCH] err1-40: sysvfs locking fix" in Linux 2.6.8 fixed the former bug by moving pointers_lock lock to the callers, but instead introduced a "sb_bread() with read_lock(&pointers_lock)" bug (which made this problem easier to hit).
Al Viro suggested that why not to do like get_branch()/get_block()/ find_shared() in Minix filesystem does. And doing like that is almost a revert of "[PATCH] err1-40: sysvfs locking fix" except that get_branch()
from with find_shared() is called without write_lock(&pointers_lock).
--- fs/sysv/itree.c | 10 ++++------ 1 file changed, 4 insertions(+), 6 deletions(-)
fs/sysv/itree.c +4 -6
@@ -82,9 +82,6 @@ static inline sysv_zone_t *block_end(struct buffer_head *bh)return (sysv_zone_t *)((char *)bh->b_data + bh->b_size); } -/* -* Requires read_lock(&pointers_lock) or write_lock(&pointers_lock) -*/ static Indirect *get_branch(struct inode *inode, int depth, int offsets[],
@@ -104,15 +101,18 @@ static Indirect *get_branch(struct inode *inode, bh =sb_bread (sb, block);if (!bh) goto failure; +read_lock (&pointers_lock);if (!verify_chain (chain, p)) goto changed;add_chain (++p, bh, (sysv_zone_t *)bh->b_data + *++offsets); +read_unlock (&pointers_lock);if (!p->key) goto no_block; }return NULL ; changed: +read_unlock (&pointers_lock);brelse (bh); *err = -EAGAIN ; goto no_block;
@@ -218,9 +218,7 @@ static int get_block(struct inode *inode, sector_t iblock, struct buffer_head *b goto out; reread: -read_lock (&pointers_lock); partial =get_branch (inode, depth, offsets, chain, &err); -read_unlock (&pointers_lock);/* Simplest case - block found, no allocation needed */ if (!partial) {
@@ -290,9 +288,9 @@ static Indirect *find_shared(struct inode *inode, *top =0 ;for (k = depth; k >1 && !offsets[k-1 ]; k--) ; + partial =get_branch (inode, k, offsets, chain, &err);write_lock (&pointers_lock); - partial =get_branch (inode, k, offsets, chain, &err);if (!partial) partial = chain + k-1 ;/*
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 261/294 scsi: lpfc: Fix possible memory leak in lpfc_rcv_padisc()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Justin Tee <[email protected]>
[ Upstream commit 2ae917d4bcab80ab304b774d492e2fcd6c52c06b ]
The call to lpfc_sli4_resume_rpi() in lpfc_rcv_padisc() may return an unsuccessful status. In such cases, the elsiocb is not issued, the completion is not called, and thus the elsiocb resource is leaked.
Check return value after calling lpfc_sli4_resume_rpi() and conditionally release the elsiocb resource.
--- drivers/scsi/lpfc/lpfc_nportdisc.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
drivers/scsi/lpfc/lpfc_nportdisc.c +4 -2
@@ -784,8 +784,10 @@ lpfc_rcv_padisc(struct lpfc_vport *vport, struct lpfc_nodelist *ndlp,/* Save the ELS cmd */ elsiocb->drvrTimeout = cmd; -lpfc_sli4_resume_rpi (ndlp, - lpfc_mbx_cmpl_resume_rpi, elsiocb); +if (lpfc_sli4_resume_rpi (ndlp, + lpfc_mbx_cmpl_resume_rpi, + elsiocb)) +kfree (elsiocb); goto out; } }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 262/294 isofs: handle CDs with bad root inode but good Joliet root directory
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alex Henrie <[email protected]>
[ Upstream commit 4243bf80c79211a8ca2795401add9c4a3b1d37ca ]
I have a CD copy of the original Tom Clancy's Ghost Recon game from 2001. The disc mounts without error on Windows, but on Linux mounting fails with the message "isofs_fill_super: get root inode failed". The error originates in isofs_read_inode, which returns -EIO because de_len is 0. The superblock on this disc appears to be intentionally corrupt as a form of copy protection.
When the root inode is unusable, instead of giving up immediately, try to continue with the Joliet file table. This fixes the Ghost Recon CD and probably other copy-protected CDs too.
Message-Id: <[email protected]>
--- fs/isofs/inode.c | 18 ++++++++++++++++-- 1 file changed, 16 insertions(+), 2 deletions(-)
fs/isofs/inode.c +16 -2
@@ -907,8 +907,22 @@ static int isofs_fill_super(struct super_block *s, void *data, int silent)* we then decide whether to use the Joliet descriptor. */ inode =isofs_iget (s, sbi->s_firstdatazone,0 ); -if (IS_ERR (inode)) - goto out_no_root; + +/* +* Fix for broken CDs with a corrupt root inode but a correct Joliet +* root directory. +*/ +if (IS_ERR (inode)) { +if (joliet_level && sbi->s_firstdatazone != first_data_zone) { +printk (KERN_NOTICE +"ISOFS: root inode is unusable. " +"Disabling Rock Ridge and switching to Joliet." ); + sbi->s_rock =0 ; + inode =NULL ; + }else { + goto out_no_root; + } + }/* * Fix for broken CDs with Rock Ridge and empty ISO root directory but
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 263/294 media: sta2x11: fix irq handler cast
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Arnd Bergmann <[email protected]>
[ Upstream commit 3de49ae81c3a0f83a554ecbce4c08e019f30168e ]
clang-16 warns about casting incompatible function pointers:
drivers/media/pci/sta2x11/sta2x11_vip.c:1057:6: error: cast from 'irqreturn_t (*)(int, struct sta2x11_vip *)' (aka 'enum irqreturn (*)(int, struct sta2x11_vip *)') to 'irq_handler_t' (aka 'enum irqreturn (*)(int, void *)') converts to incompatible function type [-Werror,-Wcast-function-type-strict]
Change the prototype of the irq handler to the regular version with a local variable to adjust the argument type.
--- drivers/media/pci/sta2x11/sta2x11_vip.c | 9 ++++----- 1 file changed, 4 insertions(+), 5 deletions(-)
drivers/media/pci/sta2x11/sta2x11_vip.c +4 -5
@@ -760,7 +760,7 @@ static const struct video_device video_dev_template = {/** * vip_irq - interrupt routine * @irq: Number of interrupt ( not used, correct number is assumed ) -* @vip: local data structure containing all information +* @data: local data structure containing all information * * check for both frame interrupts set ( top and bottom ). * check FIFO overflow, but limit number of log messages after open.
@@ -770,8 +770,9 @@ static const struct video_device video_dev_template = {* * IRQ_HANDLED, interrupt done. */ -static irqreturn_t vip_irq (int irq,struct sta2x11_vip *vip) +static irqreturn_t vip_irq (int irq,void *data) { +struct sta2x11_vip *vip = data;unsigned int status; status =reg_read (vip,DVP_ITS );
@@ -1053,9 +1054,7 @@ static int sta2x11_vip_init_one(struct pci_dev *pdev,spin_lock_init (&vip->slock); - ret =request_irq (pdev->irq, - (irq_handler_t ) vip_irq, -IRQF_SHARED ,KBUILD_MODNAME , vip); + ret =request_irq (pdev->irq, vip_irq,IRQF_SHARED ,KBUILD_MODNAME , vip);if (ret) {dev_err (&pdev->dev,"request_irq failed\n" ); ret = -ENODEV ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 264/294 ext4: add a hint for block bitmap corrupt state in mb_groups
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Zhang Yi <[email protected]>
[ Upstream commit 68ee261fb15457ecb17e3683cb4e6a4792ca5b71 ]
If one group is marked as block bitmap corrupted, its free blocks cannot be used and its free count is also deducted from the global sbi->s_freeclusters_counter. User might be confused about the absent free space because we can't query the information about corrupted block groups except unreliable error messages in syslog. So add a hint to show block bitmap corrupted groups in mb_groups.
--- fs/ext4/mballoc.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
fs/ext4/mballoc.c +4 -1
@@ -2591,7 +2591,10 @@ static int ext4_mb_seq_groups_show(struct seq_file *seq, void *v)for (i =0 ; i <=13 ; i++)seq_printf (seq," %-5u" , i <= blocksize_bits +1 ? sg.info.bb_counters[i] :0 ); -seq_puts (seq," ]\n" ); +seq_puts (seq," ]" ); +if (EXT4_MB_GRP_BBITMAP_CORRUPT (&sg.info)) +seq_puts (seq," Block bitmap corrupted!" ); +seq_puts (seq,"\n" );return 0 ; }
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 265/294 ext4: forbid commit inconsistent quota data when errors=remount-ro
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ye Bin <[email protected]>
[ Upstream commit d8b945fa475f13d787df00c26a6dc45a3e2e1d1d ]
There's issue as follows When do IO fault injection test:
Quota error (device dm-3): find_block_dqentry: Quota for id 101 referenced but not present Quota error (device dm-3): qtree_read_dquot: Can't read quota structure for id 101 Quota error (device dm-3): do_check_range: Getting block 2021161007 out of range 1-186 Quota error (device dm-3): qtree_read_dquot: Can't read quota structure for id 661
Now, ext4_write_dquot()/ext4_acquire_dquot()/ext4_release_dquot() may commit inconsistent quota data even if process failed. This may lead to filesystem corruption.
To ensure filesystem consistent when errors=remount-ro there is need to call ext4_handle_error() to abort journal.
--- fs/ext4/super.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
fs/ext4/super.c +12 -0
@@ -6205,6 +6205,10 @@ static int ext4_write_dquot(struct dquot *dquot)if (IS_ERR (handle))return PTR_ERR (handle); ret =dquot_commit (dquot); +if (ret <0 ) +ext4_error_err (dquot->dq_sb, -ret, +"Failed to commit dquot type %d" , + dquot->dq_id.type); err =ext4_journal_stop (handle);if (!ret) ret = err;
@@ -6221,6 +6225,10 @@ static int ext4_acquire_dquot(struct dquot *dquot)if (IS_ERR (handle))return PTR_ERR (handle); ret =dquot_acquire (dquot); +if (ret <0 ) +ext4_error_err (dquot->dq_sb, -ret, +"Failed to acquire dquot type %d" , + dquot->dq_id.type); err =ext4_journal_stop (handle);if (!ret) ret = err;
@@ -6240,6 +6248,10 @@ static int ext4_release_dquot(struct dquot *dquot)return PTR_ERR (handle); } ret =dquot_release (dquot); +if (ret <0 ) +ext4_error_err (dquot->dq_sb, -ret, +"Failed to release dquot type %d" , + dquot->dq_id.type); err =ext4_journal_stop (handle);if (!ret) ret = err;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 266/294 drm/amd/display: Fix nanosec stat overflow
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Aric Cyr <[email protected]>
[ Upstream commit 14d68acfd04b39f34eea7bea65dda652e6db5bf6 ]
[Why]
Nanosec stats can overflow on long running systems potentially causing statistic logging issues.
[How]
Use 64bit types for nanosec stats to ensure no overflow.
--- drivers/gpu/drm/amd/display/modules/inc/mod_stats.h | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/gpu/drm/amd/display/modules/inc/mod_stats.h +2 -2
@@ -57,10 +57,10 @@ void mod_stats_update_event(struct mod_stats *mod_stats, unsigned int length);void mod_stats_update_flip (struct mod_stats *mod_stats, -unsigned long timestamp_in_ns); +unsigned long long timestamp_in_ns);void mod_stats_update_vupdate (struct mod_stats *mod_stats, -unsigned long timestamp_in_ns); +unsigned long long timestamp_in_ns); void mod_stats_update_freesync(struct mod_stats *mod_stats, unsigned int v_total_min,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 267/294 SUNRPC: increase size of rpc_wait_queue.qlen from unsigned short to unsigned int
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Dai Ngo <[email protected]>
[ Upstream commit 2c35f43b5a4b9cdfaa6fdd946f5a212615dac8eb ]
When the NFS client is under extreme load the rpc_wait_queue.qlen counter can be overflowed. Here is an instant of the backlog queue overflow in a real world environment shown by drgn helper:
rpc_task_stats(rpc_clnt):
-------------------------rpc_clnt: 0xffff92b65d2bae00rpc_xprt: 0xffff9275db64f000
Queue: sending[64887] pending[524] backlog[30441] binding[0]
XMIT task: 0xffff925c6b1d8e98
WRITE: 750654
__dta_call_status_580: 65463
__dta_call_transmit_status_579: 1
call_reserveresult: 685189
nfs_client_init_is_complete: 1
COMMIT: 584
call_reserveresult: 573
__dta_call_status_580: 11
ACCESS: 1
__dta_call_status_580: 1
GETATTR: 10
__dta_call_status_580: 4
call_reserveresult: 6751249 tasks for server 111.222.333.444
Total tasks: 751249
count_rpc_wait_queues(xprt):
----------------------------
**** rpc_xprt: 0xffff9275db64f000 num_reqs: 65511wait_queue: xprt_binding[0] cnt: 0wait_queue: xprt_binding[1] cnt: 0wait_queue: xprt_binding[2] cnt: 0wait_queue: xprt_binding[3] cnt: 0 rpc_wait_queue[xprt_binding].qlen: 0 maxpriority: 0wait_queue: xprt_sending[0] cnt: 0wait_queue: xprt_sending[1] cnt: 64887wait_queue: xprt_sending[2] cnt: 0wait_queue: xprt_sending[3] cnt: 0 rpc_wait_queue[xprt_sending].qlen: 64887 maxpriority: 3wait_queue: xprt_pending[0] cnt: 524wait_queue: xprt_pending[1] cnt: 0wait_queue: xprt_pending[2] cnt: 0wait_queue: xprt_pending[3] cnt: 0 rpc_wait_queue[xprt_pending].qlen: 524 maxpriority: 0wait_queue: xprt_backlog[0] cnt: 0wait_queue: xprt_backlog[1] cnt: 685801wait_queue: xprt_backlog[2] cnt: 0wait_queue: xprt_backlog[3] cnt: 0 rpc_wait_queue[xprt_backlog].qlen: 30441 maxpriority: 3 [task cnt mismatch]
There is no effect on operations when this overflow occurs. However it causes confusion when trying to diagnose the performance problem.
--- include/linux/sunrpc/sched.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
include/linux/sunrpc/sched.h +1 -1
@@ -197,7 +197,7 @@ struct rpc_wait_queue {unsigned char maxpriority;/* maximum priority (0 if queue is not a priority queue) */ unsigned char priority;/* current priority */ unsigned char nr;/* # tasks remaining for cookie */ -unsigned short qlen;/* total # tasks waiting in queue */ +unsigned int qlen;/* total # tasks waiting in queue */ struct rpc_timer timer_list;#if IS_ENABLED (CONFIG_SUNRPC_DEBUG ) ||IS_ENABLED (CONFIG_TRACEPOINTS )const char * name;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 268/294 Revert "ACPI: PM: Block ASUS B1400CEAE from suspend to idle by default"
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Daniel Drake <[email protected]>
[ Upstream commit cb98555fcd8eee98c30165537c7e394f3a66e809 ]
This reverts commit d52848620de00cde4a3a5df908e231b8c8868250, which was originally put in place to work around a s2idle failure on this platform where the NVMe device was inaccessible upon resume.
After extended testing, we found that the firmware's implementation of S3 is buggy and intermittently fails to wake up the system. We need to revert to s2idle mode.
The NVMe issue has now been solved more precisely in the commit titled "PCI: Disable D3cold on Asus B1400 PCI-NVMe bridge"
--- drivers/acpi/sleep.c | 12 ------------ 1 file changed, 12 deletions(-)
drivers/acpi/sleep.c +0 -12
@@ -385,18 +385,6 @@ static const struct dmi_system_id acpisleep_dmi_table[] __initconst = { DMI_MATCH(DMI_PRODUCT_NAME, "20GGA00L00"), }, }, -/* -* ASUS B1400CEAE hangs on resume from suspend (see -* https://bugzilla.kernel.org/show_bug.cgi?id=215742). -*/ - { - .callback = init_default_s3, - .ident = "ASUS B1400CEAE", - .matches = { - DMI_MATCH(DMI_SYS_VENDOR, "ASUSTeK COMPUTER INC."), - DMI_MATCH(DMI_PRODUCT_NAME, "ASUS EXPERTBOOK B1400CEAE"), - }, - }, {}, };
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 269/294 libperf evlist: Avoid out-of-bounds access
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ian Rogers <[email protected]>
[ Upstream commit 1947b92464c3268381604bbe2ac977a3fd78192f ]
Parallel testing appears to show a race between allocating and setting evsel ids. As there is a bounds check on the xyarray it yields a segv like:
```
AddressSanitizer:DEADLYSIGNAL
=================================================================
==484408==ERROR: AddressSanitizer: SEGV on unknown address 0x000000000010
==484408==The signal is caused by a WRITE memory access.
==484408==Hint: address points to the zero page.
#0 0x55cef5d4eff4 in perf_evlist__id_hash tools/lib/perf/evlist.c:256
#1 0x55cef5d4f132 in perf_evlist__id_add tools/lib/perf/evlist.c:274
#2 0x55cef5d4f545 in perf_evlist__id_add_fd tools/lib/perf/evlist.c:315
#3 0x55cef5a1923f in store_evsel_ids util/evsel.c:3130
#4 0x55cef5a19400 in evsel__store_ids util/evsel.c:3147
#5 0x55cef5888204 in __run_perf_stat tools/perf/builtin-stat.c:832
#6 0x55cef5888c06 in run_perf_stat tools/perf/builtin-stat.c:960
#7 0x55cef58932db in cmd_stat tools/perf/builtin-stat.c:2878
...
```Avoid this crash by early exiting the perf_evlist__id_add_fd and perf_evlist__id_add is the access is out-of-bounds.
--- tools/lib/perf/evlist.c | 18 ++++++++++++------ tools/lib/perf/include/internal/evlist.h | 4 ++-- 2 files changed, 14 insertions(+), 8 deletions(-)
tools/lib/perf/evlist.c +12 -6
@@ -226,10 +226,10 @@ u64 perf_evlist__read_format(struct perf_evlist *evlist)static void perf_evlist__id_hash (struct perf_evlist *evlist,struct perf_evsel *evsel, -int cpu,int thread,u64 id) +int cpu_map_idx,int thread,u64 id) {int hash; -struct perf_sample_id *sid =SID (evsel, cpu, thread); +struct perf_sample_id *sid =SID (evsel, cpu_map_idx, thread); sid->id = id; sid->evsel = evsel;
@@ -239,21 +239,27 @@ static void perf_evlist__id_hash(struct perf_evlist *evlist,void perf_evlist__id_add (struct perf_evlist *evlist,struct perf_evsel *evsel, -int cpu,int thread,u64 id) +int cpu_map_idx,int thread,u64 id) { -perf_evlist__id_hash (evlist, evsel, cpu, thread, id); +if (!SID (evsel, cpu_map_idx, thread)) +return ; + +perf_evlist__id_hash (evlist, evsel, cpu_map_idx, thread, id); evsel->id[evsel->ids++] = id; }int perf_evlist__id_add_fd (struct perf_evlist *evlist,struct perf_evsel *evsel, -int cpu,int thread,int fd) +int cpu_map_idx,int thread,int fd) {u64 read_data[4 ] = {0 , };int id_idx =1 ;/* The first entry is the counter value */ u64 id;int ret; +if (!SID (evsel, cpu_map_idx, thread)) +return -1 ; + ret =ioctl (fd,PERF_EVENT_IOC_ID , &id);if (!ret) goto add;
@@ -282,7 +288,7 @@ int perf_evlist__id_add_fd(struct perf_evlist *evlist, id = read_data[id_idx]; add: -perf_evlist__id_add (evlist, evsel, cpu, thread, id); +perf_evlist__id_add (evlist, evsel, cpu_map_idx, thread, id);return 0 ; }
tools/lib/perf/include/internal/evlist.h +2 -2
@@ -118,10 +118,10 @@ u64 perf_evlist__read_format(struct perf_evlist *evlist);void perf_evlist__id_add (struct perf_evlist *evlist,struct perf_evsel *evsel, -int cpu,int thread,u64 id); +int cpu_map_idx,int thread,u64 id);int perf_evlist__id_add_fd (struct perf_evlist *evlist,struct perf_evsel *evsel, -int cpu,int thread,int fd); +int cpu_map_idx,int thread,int fd);#endif /* __LIBPERF_INTERNAL_EVLIST_H */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 270/294 block: prevent division by zero in blk_rq_stat_sum()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Roman Smirnov <[email protected]>
[ Upstream commit 93f52fbeaf4b676b21acfe42a5152620e6770d02 ]
The expression dst->nr_samples + src->nr_samples may have zero value on overflow. It is necessary to add a check to avoid division by zero.
Found by Linux Verification Center (linuxtesting.org) with Svace.
--- block/blk-stat.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
block/blk-stat.c +1 -1
@@ -28,7 +28,7 @@ void blk_rq_stat_init(struct blk_rq_stat *stat)/* src is a per-cpu stat, mean isn't initialized */ void blk_rq_stat_sum (struct blk_rq_stat *dst,struct blk_rq_stat *src) { -if (!src->nr_samples) +if (dst->nr_samples + src->nr_samples <= dst->nr_samples)return ; dst->min =min (dst->min, src->min);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 271/294 RDMA/cm: add timeout to cm_destroy_id wait
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Manjunath Patil <[email protected]>
[ Upstream commit 96d9cbe2f2ff7abde021bac75eafaceabe9a51fa ]
Add timeout to cm_destroy_id, so that userspace can trigger any data collection that would help in analyzing the cause of delay in destroying the cm_id.
New noinline function helps dtrace/ebpf programs to hook on to it. Existing functionality isn't changed except triggering a probe-able new function at every timeout interval.
We have seen cases where CM messages stuck with MAD layer (either due to software bug or faulty HCA), leading to cm_id getting stuck in the following call stack. This patch helps in resolving such issues faster.
kernel: ... INFO: task XXXX:56778 blocked for more than 120 seconds.
...
Call Trace: __schedule+0x2bc/0x895 schedule+0x36/0x7c schedule_timeout+0x1f6/0x31f ? __slab_free+0x19c/0x2ba wait_for_completion+0x12b/0x18a ? wake_up_q+0x80/0x73 cm_destroy_id+0x345/0x610 [ib_cm] ib_destroy_cm_id+0x10/0x20 [ib_cm] rdma_destroy_id+0xa8/0x300 [rdma_cm] ucma_destroy_id+0x13e/0x190 [rdma_ucm] ucma_write+0xe0/0x160 [rdma_ucm] __vfs_write+0x3a/0x16d vfs_write+0xb2/0x1a1 ? syscall_trace_enter+0x1ce/0x2b8 SyS_write+0x5c/0xd3 do_syscall_64+0x79/0x1b9 entry_SYSCALL_64_after_hwframe+0x16d/0x0
--- drivers/infiniband/core/cm.c | 20 +++++++++++++++++++- 1 file changed, 19 insertions(+), 1 deletion(-)
drivers/infiniband/core/cm.c +19 -1
@@ -33,6 +33,7 @@ MODULE_AUTHOR("Sean Hefty");MODULE_DESCRIPTION ("InfiniBand CM" );MODULE_LICENSE ("Dual BSD/GPL" ); +#define CM_DESTROY_ID_WAIT_TIMEOUT 10000/* msecs */ static const char *const ibcm_rej_reason_strs[] = { [IB_CM_REJ_NO_QP ] ="no QP" , [IB_CM_REJ_NO_EEC ] ="no EEC" ,
@@ -1056,10 +1057,20 @@ static void cm_reset_to_idle(struct cm_id_private *cm_id_priv) } } +static noinline void cm_destroy_id_wait_timeout(struct ib_cm_id *cm_id) +{ +struct cm_id_private *cm_id_priv; + + cm_id_priv = container_of(cm_id, struct cm_id_private, id); +pr_err ("%s: cm_id=%p timed out. state=%d refcnt=%d\n" , __func__, + cm_id, cm_id->state,refcount_read (&cm_id_priv->refcount)); +} +static void cm_destroy_id (struct ib_cm_id *cm_id,int err) {struct cm_id_private *cm_id_priv;struct cm_work *work; +int ret; cm_id_priv = container_of(cm_id, struct cm_id_private, id);spin_lock_irq (&cm_id_priv->lock);
@@ -1171,7 +1182,14 @@ static void cm_destroy_id(struct ib_cm_id *cm_id, int err)xa_erase (&cm.local_id_table,cm_local_id (cm_id->local_id));cm_deref_id (cm_id_priv); -wait_for_completion (&cm_id_priv->comp); +do { + ret =wait_for_completion_timeout (&cm_id_priv->comp, +msecs_to_jiffies ( +CM_DESTROY_ID_WAIT_TIMEOUT )); +if (!ret)/* timeout happened */ +cm_destroy_id_wait_timeout (cm_id); + }while (!ret); +while ((work =cm_dequeue_work (cm_id_priv)) !=NULL )cm_free_work (work);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 272/294 Input: allocate keycode for Display refresh rate toggle
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Gergo Koteles <[email protected]>
[ Upstream commit cfeb98b95fff25c442f78a6f616c627bc48a26b7 ]
Newer Lenovo Yogas and Legions with 60Hz/90Hz displays send a wmi event when Fn + R is pressed. This is intended for use to switch between the two refresh rates.
Allocate a new KEY_REFRESH_RATE_TOGGLE keycode for it.
--- include/uapi/linux/input-event-codes.h | 1 + 1 file changed, 1 insertion(+)
include/uapi/linux/input-event-codes.h +1 -0
@@ -602,6 +602,7 @@#define KEY_ALS_TOGGLE 0x230/* Ambient light sensor */ #define KEY_ROTATE_LOCK_TOGGLE 0x231/* Display rotation lock */ +#define KEY_REFRESH_RATE_TOGGLE 0x232/* Display refresh rate toggle */ #define KEY_BUTTONCONFIG 0x240/* AL Button Configuration */ #define KEY_TASKMANAGER 0x241/* AL Task/Project Manager */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 273/294 platform/x86: touchscreen_dmi: Add an extra entry for a variant of the Chuwi Vi8 tablet
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Alban Boyé <[email protected]>
[ Upstream commit 1266e2efb7512dbf20eac820ca2ed34de6b1c3e7 ]
--- drivers/platform/x86/touchscreen_dmi.c | 9 +++++++++ 1 file changed, 9 insertions(+)
drivers/platform/x86/touchscreen_dmi.c +9 -0
@@ -1084,6 +1084,15 @@ const struct dmi_system_id touchscreen_dmi_table[] = { DMI_MATCH(DMI_BIOS_VERSION, "CHUWI.D86JLBNR"), }, }, + { +/* Chuwi Vi8 dual-boot (CWI506) */ + .driver_data = (void *)&chuwi_vi8_data, + .matches = { +DMI_MATCH (DMI_SYS_VENDOR ,"Insyde" ), +DMI_MATCH (DMI_PRODUCT_NAME ,"i86" ), + DMI_MATCH(DMI_BIOS_VERSION, "CHUWI2.D86JHBNR02"), + }, + }, {/* Chuwi Vi8 Plus (CWI519) */ .driver_data = (void *)&chuwi_vi8_plus_data,
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 274/294 ktest: force $buildonly = 1 for make_warnings_file test type
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Ricardo B. Marliere <[email protected]>
[ Upstream commit 07283c1873a4d0eaa0e822536881bfdaea853910 ]
The test type "make_warnings_file" should have no mandatory configuration parameters other than the ones required by the "build" test type, because its purpose is to create a file with build warnings that may or may not be used by other subsequent tests. Currently, the only way to use it as a stand-alone test is by setting POWER_CYCLE, CONSOLE, SSH_USER, BUILD_TARGET, TARGET_IMAGE, REBOOT_TYPE and GRUB_MENU.
--- tools/testing/ktest/ktest.pl | 1 + 1 file changed, 1 insertion(+)
tools/testing/ktest/ktest.pl +1 -0
@@ -773,6 +773,7 @@ sub set_value { if ($lvalue =~ /^(TEST|BISECT|CONFIG_BISECT)_TYPE(\[.*\])?$/ && $prvalue !~ /^(config_|)bisect$/ && $prvalue !~ /^build$/ && + $prvalue !~ /^make_warnings_file$/ && $buildonly) { # Note if a test is something other than build, then we
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 275/294 ring-buffer: use READ_ONCE() to read cpu_buffer->commit_page in concurrent environment
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: linke li <[email protected]>
[ Upstream commit f1e30cb6369251c03f63c564006f96a54197dcc4 ]
In function ring_buffer_iter_empty(), cpu_buffer->commit_page is read while other threads may change it. It may cause the time_stamp that read in the next line come from a different page. Use READ_ONCE() to avoid having to reason about compiler optimizations now and in future.
--- kernel/trace/ring_buffer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
kernel/trace/ring_buffer.c +1 -1
@@ -4211,7 +4211,7 @@ int ring_buffer_iter_empty(struct ring_buffer_iter *iter) cpu_buffer = iter->cpu_buffer; reader = cpu_buffer->reader_page; head_page = cpu_buffer->head_page; - commit_page = cpu_buffer->commit_page; + commit_page =READ_ONCE (cpu_buffer->commit_page); commit_ts = commit_page->page->time_stamp;/*
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 276/294 tools: iio: replace seekdir() in iio_generic_buffer
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Petre Rodan <[email protected]>
[ Upstream commit 4e6500bfa053dc133021f9c144261b77b0ba7dc8 ]
Replace seekdir() with rewinddir() in order to fix a localized glibc bug.
One of the glibc patches that stable Gentoo is using causes an improper directory stream positioning bug on 32bit arm. That in turn ends up as a floating point exception in iio_generic_buffer.
The attached patch provides a fix by using an equivalent function which should not cause trouble for other distros and is easier to reason about in general as it obviously always goes back to to the start.
https://sourceware.org/bugzilla/show_bug.cgi?id=31212
--- tools/iio/iio_utils.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
tools/iio/iio_utils.c +1 -1
@@ -373,7 +373,7 @@ int build_channel_array(const char *device_dir, goto error_close_dir; } -seekdir (dp,0 ); +rewinddir (dp);while (ent =readdir (dp), ent) {if (strcmp (ent->d_name +strlen (ent->d_name) -strlen ("_en" ),"_en" ) ==0 ) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 277/294 usb: typec: tcpci: add generic tcpci fallback compatible
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Marco Felsch <[email protected]>
[ Upstream commit 8774ea7a553e2aec323170d49365b59af0a2b7e0 ]
The driver already support the tcpci binding for the i2c_device_id so add the support for the of_device_id too.
--- drivers/usb/typec/tcpm/tcpci.c | 1 + 1 file changed, 1 insertion(+)
drivers/usb/typec/tcpm/tcpci.c +1 -0
@@ -732,6 +732,7 @@ MODULE_DEVICE_TABLE(i2c, tcpci_id);#ifdef CONFIG_OF static const struct of_device_id tcpci_of_match[] = { { .compatible ="nxp,ptn5110" , }, + { .compatible ="tcpci" , }, {}, };MODULE_DEVICE_TABLE (of, tcpci_of_match);
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 278/294 usb: sl811-hcd: only defined function checkdone if QUIRK2 is defined
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Colin Ian King <[email protected]>
[ Upstream commit 12f371e2b6cb4b79c788f1f073992e115f4ca918 ]
Function checkdone is only required if QUIRK2 is defined, so add appropriate #if / #endif around the function.
Cleans up clang scan build warning:drivers/usb/host/sl811-hcd.c:588:18: warning: unused function 'checkdone' [-Wunused-function]
--- drivers/usb/host/sl811-hcd.c | 2 ++ 1 file changed, 2 insertions(+)
drivers/usb/host/sl811-hcd.c +2 -0
@@ -585,6 +585,7 @@ done(struct sl811 *sl811, struct sl811h_ep *ep, u8 bank)finish_request (sl811, ep, urb, urbstat); } +#ifdef QUIRK2 static inline u8 checkdone (struct sl811 *sl811) {u8 ctl;
@@ -616,6 +617,7 @@ static inline u8 checkdone(struct sl811 *sl811)#endif return irqstat; } +#endif static irqreturn_t sl811h_irq (struct usb_hcd *hcd) {
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 279/294 fbdev: viafb: fix typo in hw_bitblt_1 and hw_bitblt_2
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Aleksandr Burakov <[email protected]>
[ Upstream commit bc87bb342f106a0402186bcb588fcbe945dced4b ]
There are some actions with value 'tmp' but 'dst_addr' is checked instead. It is obvious that a copy-paste error was made here and the value of variable 'tmp' should be checked here.
Found by Linux Verification Center (linuxtesting.org) with SVACE.
--- drivers/video/fbdev/via/accel.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
drivers/video/fbdev/via/accel.c +2 -2
@@ -115,7 +115,7 @@ static int hw_bitblt_1(void __iomem *engine, u8 op, u32 width, u32 height,if (op !=VIA_BITBLT_FILL ) { tmp = src_mem ?0 : src_addr; -if (dst_addr &0xE0000007 ) { +if (tmp &0xE0000007 ) {printk (KERN_WARNING "hw_bitblt_1: Unsupported source " "address %X\n" , tmp);return -EINVAL ;
@@ -260,7 +260,7 @@ static int hw_bitblt_2(void __iomem *engine, u8 op, u32 width, u32 height,writel (tmp, engine +0x18 ); tmp = src_mem ?0 : src_addr; -if (dst_addr &0xE0000007 ) { +if (tmp &0xE0000007 ) {printk (KERN_WARNING "hw_bitblt_2: Unsupported source " "address %X\n" , tmp);return -EINVAL ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 280/294 drivers/nvme: Add quirks for device 126f:2262
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Jiawei Fu (iBug) <[email protected]>
[ Upstream commit e89086c43f0500bc7c4ce225495b73b8ce234c1f ]
This commit adds NVME_QUIRK_NO_DEEPEST_PS and NVME_QUIRK_BOGUS_NID for device [126f:2262], which appears to be a generic VID:PID pair used for many SSDs based on the Silicon Motion SM2262/SM2262EN controller.
Two of my SSDs with this VID:PID pair exhibit the same behavior:
* They frequently have trouble exiting the deepest power state (5), resulting in the entire disk unresponsive.
Verified by setting nvme_core.default_ps_max_latency_us=10000 and observing them behaving normally.
* They produce all-zero nguid and eui64 with nvme id-ns command.
The offending products are:
* HP SSD EX950 1TB
* HIKVISION C2000Pro 2TB
--- drivers/nvme/host/pci.c | 3 +++ 1 file changed, 3 insertions(+)
drivers/nvme/host/pci.c +3 -0
@@ -3199,6 +3199,9 @@ static const struct pci_device_id nvme_id_table[] = { NVME_QUIRK_BOGUS_NID, }, { PCI_VDEVICE(REDHAT, 0x0010), /* Qemu emulated controller */ .driver_data = NVME_QUIRK_BOGUS_NID, }, + { PCI_DEVICE(0x126f, 0x2262), /* Silicon Motion generic */ + .driver_data = NVME_QUIRK_NO_DEEPEST_PS | + NVME_QUIRK_BOGUS_NID, }, { PCI_DEVICE(0x126f, 0x2263), /* Silicon Motion unidentified */ .driver_data = NVME_QUIRK_NO_NS_DESC_LIST, }, { PCI_DEVICE(0x1bb1, 0x0100), /* Seagate Nytro Flash Storage */
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 281/294 fbmon: prevent division by zero in fb_videomode_from_videomode()
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Roman Smirnov <[email protected]>
[ Upstream commit c2d953276b8b27459baed1277a4fdd5dd9bd4126 ]
The expression htotal * vtotal can have a zero value on overflow. It is necessary to prevent division by zero like in fb_var_to_videomode().
Found by Linux Verification Center (linuxtesting.org) with Svace.
--- drivers/video/fbdev/core/fbmon.c | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-)
drivers/video/fbdev/core/fbmon.c +4 -3
@@ -1311,7 +1311,7 @@ int fb_get_mode(int flags, u32 val, struct fb_var_screeninfo *var, struct fb_infint fb_videomode_from_videomode (const struct videomode *vm,struct fb_videomode *fbmode) { -unsigned int htotal, vtotal; +unsigned int htotal, vtotal, total; fbmode->xres = vm->hactive; fbmode->left_margin = vm->hback_porch;
@@ -1344,8 +1344,9 @@ int fb_videomode_from_videomode(const struct videomode *vm, vtotal = vm->vactive + vm->vfront_porch + vm->vback_porch + vm->vsync_len;/* prevent division by zero */ -if (htotal && vtotal) { - fbmode->refresh = vm->pixelclock / (htotal * vtotal); + total = htotal * vtotal; +if (total) { + fbmode->refresh = vm->pixelclock / total;/* a mode must have htotal and vtotal != 0 or it is invalid */ }else { fbmode->refresh =0 ;
Signature · 1 line
2.43.0
Greg Kroah-Hartman
maintainerPATCH 282/294 netfilter: nf_tables: release batch on table validation from abort path
In reply to Greg Kroah-Hartman5.10-stable review patch. If anyone has any objections, please let me know.
------------------
From: Pablo Neira Ayuso <[email protected]>
commit a45e6889575c2067d3c0212b6bc1022891e65b91 upstream.
Unlike early commit path stage which triggers a call to abort, an explicit release of the batch is required on abort, otherwise mutex is released and commit_list remains in place.
Add WARN_ON_ONCE to ensure commit_list is empty from the abort path before releasing the mutex.
After this patch, commit_list is always assumed to be empty before grabbing the mutex, therefore
03c1f1ef1584 ("netfilter: Cleanup nft_net->module_list from nf_tables_exit_net()")
only needs to release the pending modules for registration.
--- net/netfilter/nf_tables_api.c | 14 ++++++++++---- 1 file changed, 10 insertions(+), 4 deletions(-)
net/netfilter/nf_tables_api.c +10 -4
@@ -8800,10 +8800,11 @@ static int __nf_tables_abort(struct net *net, enum nfnl_abort_action action)struct nft_trans *trans, *next;LIST_HEAD (set_update_list);struct nft_trans_elem *te; +int err =0 ;if (action ==NFNL_ABORT_VALIDATE &&nf_tables_validate (net) <0 ) -return -EAGAIN ; + err = -EAGAIN ;list_for_each_entry_safe_reverse (trans, next, &nft_net->commit_list, list) {
@@ -8968,7 +8969,7 @@ static int __nf_tables_abort(struct net *net, enum nfnl_abort_action action)else nf_tables_module_autoload_cleanup (net); -return 0 ; +return err; } static int nf_tables_abort(struct net *net, struct sk_buff *skb,
@@ -8982,6 +8983,8 @@ static int nf_tables_abort(struct net *net, struct sk_buff *skb, ret =__nf_tables_abort (net, action);nft_gc_seq_end (nft_net, gc_seq); +WARN_ON_ONCE (!list_empty (&nft_net->commit_list)); +mutex_unlock (&nft_net->commit_mutex);return ret;
@@ -9716,8 +9719,11 @@ static void __net_exit nf_tables_exit_net(struct net *net) gc_seq =nft_gc_seq_begin (nft_net); -if (!list_empty (&nft_net->commit_list)) -__nf_tables_abort (net,NFNL_ABORT_NONE ); +WARN_ON_ONCE (!list_empty (&nft_net->commit_list)); + +if (!list_empty (&nft_net->module_list)) +nf_tables_module_autoload_cleanup (net); +__nft_release_tables (net);nft_gc_seq_end (nft_net, gc_seq);
Signature · 1 line
2.43.0