From: Aurelien Aptel aaptel@suse.com
[ Upstream commit bc31d0cdcfbadb6258b45db97e93b1c83822ba33 ]
We have a customer reporting crashes in lock_get_status() with many "Leaked POSIX lock" messages preceeding the crash.
Leaked POSIX lock on dev=0x0:0x56 ... Leaked POSIX lock on dev=0x0:0x56 ... Leaked POSIX lock on dev=0x0:0x56 ... Leaked POSIX lock on dev=0x0:0x53 ... Leaked POSIX lock on dev=0x0:0x53 ... Leaked POSIX lock on dev=0x0:0x53 ... Leaked POSIX lock on dev=0x0:0x53 ... POSIX: fl_owner=ffff8900e7b79380 fl_flags=0x1 fl_type=0x1 fl_pid=20709 Leaked POSIX lock on dev=0x0:0x4b ino... Leaked locks on dev=0x0:0x4b ino=0xf911400000029: POSIX: fl_owner=ffff89f41c870e00 fl_flags=0x1 fl_type=0x1 fl_pid=19592 stack segment: 0000 [#1] SMP Modules linked in: binfmt_misc msr tcp_diag udp_diag inet_diag unix_diag af_packet_diag netlink_diag rpcsec_gss_krb5 arc4 ecb auth_rpcgss nfsv4 md4 nfs nls_utf8 lockd grace cifs sunrpc ccm dns_resolver fscache af_packet iscsi_ibft iscsi_boot_sysfs vmw_vsock_vmci_transport vsock xfs libcrc32c sb_edac edac_core crct10dif_pclmul crc32_pclmul ghash_clmulni_intel drbg ansi_cprng vmw_balloon aesni_intel aes_x86_64 lrw gf128mul glue_helper ablk_helper cryptd joydev pcspkr vmxnet3 i2c_piix4 vmw_vmci shpchp fjes processor button ac btrfs xor raid6_pq sr_mod cdrom ata_generic sd_mod ata_piix vmwgfx crc32c_intel drm_kms_helper syscopyarea sysfillrect sysimgblt fb_sys_fops ttm serio_raw ahci libahci drm libata vmw_pvscsi sg dm_multipath dm_mod scsi_dh_rdac scsi_dh_emc scsi_dh_alua scsi_mod autofs4
Supported: Yes CPU: 6 PID: 28250 Comm: lsof Not tainted 4.4.156-94.64-default #1 Hardware name: VMware, Inc. VMware Virtual Platform/440BX Desktop Reference Platform, BIOS 6.00 04/05/2016 task: ffff88a345f28740 ti: ffff88c74005c000 task.ti: ffff88c74005c000 RIP: 0010:[<ffffffff8125dcab>] [<ffffffff8125dcab>] lock_get_status+0x9b/0x3b0 RSP: 0018:ffff88c74005fd90 EFLAGS: 00010202 RAX: ffff89bde83e20ae RBX: ffff89e870003d18 RCX: 0000000049534f50 RDX: ffffffff81a3541f RSI: ffffffff81a3544e RDI: ffff89bde83e20ae RBP: 0026252423222120 R08: 0000000020584953 R09: 000000000000ffff R10: 0000000000000000 R11: ffff88c74005fc70 R12: ffff89e5ca7b1340 R13: 00000000000050e5 R14: ffff89e870003d30 R15: ffff89e5ca7b1340 FS: 00007fafd64be800(0000) GS:ffff89f41fd00000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000001c80018 CR3: 000000a522048000 CR4: 0000000000360670 DR0: 0000000000000000 DR1: 0000000000000000 DR2: 0000000000000000 DR3: 0000000000000000 DR6: 00000000fffe0ff0 DR7: 0000000000000400 Stack: 0000000000000208 ffffffff81a3d6b6 ffff89e870003d30 ffff89e870003d18 ffff89e5ca7b1340 ffff89f41738d7c0 ffff89e870003d30 ffff89e5ca7b1340 ffffffff8125e08f 0000000000000000 ffff89bc22b67d00 ffff88c74005ff28 Call Trace: [<ffffffff8125e08f>] locks_show+0x2f/0x70 [<ffffffff81230ad1>] seq_read+0x251/0x3a0 [<ffffffff81275bbc>] proc_reg_read+0x3c/0x70 [<ffffffff8120e456>] __vfs_read+0x26/0x140 [<ffffffff8120e9da>] vfs_read+0x7a/0x120 [<ffffffff8120faf2>] SyS_read+0x42/0xa0 [<ffffffff8161cbc3>] entry_SYSCALL_64_fastpath+0x1e/0xb7
When Linux closes a FD (close(), close-on-exec, dup2(), ...) it calls filp_close() which also removes all posix locks.
The lock struct is initialized like so in filp_close() and passed down to cifs
... lock.fl_type = F_UNLCK; lock.fl_flags = FL_POSIX | FL_CLOSE; lock.fl_start = 0; lock.fl_end = OFFSET_MAX; ...
Note the FL_CLOSE flag, which hints the VFS code that this unlocking is done for closing the fd.
filp_close() locks_remove_posix(filp, id); vfs_lock_file(filp, F_SETLK, &lock, NULL); return filp->f_op->lock(filp, cmd, fl) => cifs_lock() rc = cifs_setlk(file, flock, type, wait_flag, posix_lck, lock, unlock, xid); rc = server->ops->mand_unlock_range(cfile, flock, xid); if (flock->fl_flags & FL_POSIX && !rc) rc = locks_lock_file_wait(file, flock)
Notice how we don't call locks_lock_file_wait() which does the generic VFS lock/unlock/wait work on the inode if rc != 0.
If we are closing the handle, the SMB server is supposed to remove any locks associated with it. Similarly, cifs.ko frees and wakes up any lock and lock waiter when closing the file:
cifs_close() cifsFileInfo_put(file->private_data) /* * Delete any outstanding lock records. We'll lose them when the file * is closed anyway. */ down_write(&cifsi->lock_sem); list_for_each_entry_safe(li, tmp, &cifs_file->llist->locks, llist) { list_del(&li->llist); cifs_del_lock_waiters(li); kfree(li); } list_del(&cifs_file->llist->llist); kfree(cifs_file->llist); up_write(&cifsi->lock_sem);
So we can safely ignore unlocking failures in cifs_lock() if they happen with the FL_CLOSE flag hint set as both the server and the client take care of it during the actual closing.
This is not a proper fix for the unlocking failure but it's safe and it seems to prevent the lock leakages and crashes the customer experiences.
Signed-off-by: Aurelien Aptel aaptel@suse.com Signed-off-by: NeilBrown neil@brown.name Signed-off-by: Steve French stfrench@microsoft.com Acked-by: Pavel Shilovsky pshilov@microsoft.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/cifs/file.c | 14 +++++++++++++- 1 file changed, 13 insertions(+), 1 deletion(-)
diff --git a/fs/cifs/file.c b/fs/cifs/file.c index 1c5099fffaec..7d295bf283ca 100644 --- a/fs/cifs/file.c +++ b/fs/cifs/file.c @@ -1627,8 +1627,20 @@ cifs_setlk(struct file *file, struct file_lock *flock, __u32 type, rc = server->ops->mand_unlock_range(cfile, flock, xid);
out: - if (flock->fl_flags & FL_POSIX && !rc) + if (flock->fl_flags & FL_POSIX) { + /* + * If this is a request to remove all locks because we + * are closing the file, it doesn't matter if the + * unlocking failed as both cifs.ko and the SMB server + * remove the lock on file close + */ + if (rc) { + cifs_dbg(VFS, "%s failed rc=%d\n", __func__, rc); + if (!(flock->fl_flags & FL_CLOSE)) + return rc; + } rc = locks_lock_file_wait(file, flock); + } return rc; }
From: Masahiro Yamada yamada.masahiro@socionext.com
[ Upstream commit fc2b47b55f17fd996f7a01975ce1c33c2f2513f6 ]
It believe it is a bad idea to hardcode a specific compiler prefix that may or may not be installed on a user's system. It is annoying when testing features that should not require compilers at all.
For example, mrproper, headers_install, etc. should work without any compiler.
They look like follows on my machine.
$ make ARCH=h8300 mrproper ./scripts/gcc-version.sh: line 26: h8300-unknown-linux-gcc: command not found ./scripts/gcc-version.sh: line 27: h8300-unknown-linux-gcc: command not found make: h8300-unknown-linux-gcc: Command not found make: h8300-unknown-linux-gcc: Command not found [ a bunch of the same error messages continue ]
$ make ARCH=h8300 headers_install ./scripts/gcc-version.sh: line 26: h8300-unknown-linux-gcc: command not found ./scripts/gcc-version.sh: line 27: h8300-unknown-linux-gcc: command not found make: h8300-unknown-linux-gcc: Command not found HOSTCC scripts/basic/fixdep make: h8300-unknown-linux-gcc: Command not found WRAP arch/h8300/include/generated/uapi/asm/kvm_para.h [ snip ]
The solution is to delete this line, or to use cc-cross-prefix like some architectures do. I chose the latter as a moderate fixup.
I added an alternative 'h8300-linux-' because it is available at:
https://mirrors.edge.kernel.org/pub/tools/crosstool/files/bin/x86_64/8.1.0/
Signed-off-by: Masahiro Yamada yamada.masahiro@socionext.com Signed-off-by: Sasha Levin sashal@kernel.org --- arch/h8300/Makefile | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/h8300/Makefile b/arch/h8300/Makefile index e1c02ca230cb..073bba6f9f60 100644 --- a/arch/h8300/Makefile +++ b/arch/h8300/Makefile @@ -23,7 +23,7 @@ KBUILD_AFLAGS += $(aflags-y) LDFLAGS += $(ldflags-y)
ifeq ($(CROSS_COMPILE),) -CROSS_COMPILE := h8300-unknown-linux- +CROSS_COMPILE := $(call cc-cross-prefix, h8300-unknown-linux- h8300-linux-) endif
core-y += arch/$(ARCH)/kernel/ arch/$(ARCH)/mm/
From: Louis Taylor louis@kragniz.eu
[ Upstream commit 60f7691c624b41a05bfc3493d9b0519e7951b7ef ]
When compiling with -Wformat, clang warns:
drivers/i2c/busses/i2c-sis630.c:482:4: warning: format specifies type 'unsigned short' but the argument has type 'int' [-Wformat] smbus_base + SMB_STS, ^~~~~~~~~~~~~~~~~~~~
drivers/i2c/busses/i2c-sis630.c:483:4: warning: format specifies type 'unsigned short' but the argument has type 'int' [-Wformat] smbus_base + SMB_STS + SIS630_SMB_IOREGION - 1); ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
drivers/i2c/busses/i2c-sis630.c:531:37: warning: format specifies type 'unsigned short' but the argument has type 'int' [-Wformat] "SMBus SIS630 adapter at %04hx", smbus_base + SMB_STS); ~~~~~ ^~~~~~~~~~~~~~~~~~~~
This patch fixes the format strings to use the format type for int.
Link: https://github.com/ClangBuiltLinux/linux/issues/378 Signed-off-by: Louis Taylor louis@kragniz.eu Reviewed-by: Nick Desaulniers ndesaulniers@google.com Reviewed-by: Jean Delvare jdelvare@suse.de Signed-off-by: Wolfram Sang wsa@the-dreams.de Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/i2c/busses/i2c-sis630.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/i2c/busses/i2c-sis630.c b/drivers/i2c/busses/i2c-sis630.c index 1e6805b5cef2..a57aa4fe51a4 100644 --- a/drivers/i2c/busses/i2c-sis630.c +++ b/drivers/i2c/busses/i2c-sis630.c @@ -478,7 +478,7 @@ static int sis630_setup(struct pci_dev *sis630_dev) if (!request_region(smbus_base + SMB_STS, SIS630_SMB_IOREGION, sis630_driver.name)) { dev_err(&sis630_dev->dev, - "I/O Region 0x%04hx-0x%04hx for SMBus already in use.\n", + "I/O Region 0x%04x-0x%04x for SMBus already in use.\n", smbus_base + SMB_STS, smbus_base + SMB_STS + SIS630_SMB_IOREGION - 1); retval = -EBUSY; @@ -528,7 +528,7 @@ static int sis630_probe(struct pci_dev *dev, const struct pci_device_id *id) sis630_adapter.dev.parent = &dev->dev;
snprintf(sis630_adapter.name, sizeof(sis630_adapter.name), - "SMBus SIS630 adapter at %04hx", smbus_base + SMB_STS); + "SMBus SIS630 adapter at %04x", smbus_base + SMB_STS);
return i2c_add_adapter(&sis630_adapter); }
From: Douglas Anderson dianders@chromium.org
[ Upstream commit 31b265b3baaf55f209229888b7ffea523ddab366 ]
As reported back in 2016-11 [1], the "ftdump" kdb command triggers a BUG for "sleeping function called from invalid context".
kdb's "ftdump" command wants to call ring_buffer_read_prepare() in atomic context. A very simple solution for this is to add allocation flags to ring_buffer_read_prepare() so kdb can call it without triggering the allocation error. This patch does that.
Note that in the original email thread about this, it was suggested that perhaps the solution for kdb was to either preallocate the buffer ahead of time or create our own iterator. I'm hoping that this alternative of adding allocation flags to ring_buffer_read_prepare() can be considered since it means I don't need to duplicate more of the core trace code into "trace_kdb.c" (for either creating my own iterator or re-preparing a ring allocator whose memory was already allocated).
NOTE: another option for kdb is to actually figure out how to make it reuse the existing ftrace_dump() function and totally eliminate the duplication. This sounds very appealing and actually works (the "sr z" command can be seen to properly dump the ftrace buffer). The downside here is that ftrace_dump() fully consumes the trace buffer. Unless that is changed I'd rather not use it because it means "ftdump | grep xyz" won't be very useful to search the ftrace buffer since it will throw away the whole trace on the first grep. A future patch to dump only the last few lines of the buffer will also be hard to implement.
[1] https://lkml.kernel.org/r/20161117191605.GA21459@google.com
Link: http://lkml.kernel.org/r/20190308193205.213659-1-dianders@chromium.org
Reported-by: Brian Norris briannorris@chromium.org Signed-off-by: Douglas Anderson dianders@chromium.org Signed-off-by: Steven Rostedt (VMware) rostedt@goodmis.org Signed-off-by: Sasha Levin sashal@kernel.org --- include/linux/ring_buffer.h | 2 +- kernel/trace/ring_buffer.c | 5 +++-- kernel/trace/trace.c | 6 ++++-- kernel/trace/trace_kdb.c | 6 ++++-- 4 files changed, 12 insertions(+), 7 deletions(-)
diff --git a/include/linux/ring_buffer.h b/include/linux/ring_buffer.h index 19d0778ec382..121c8f99ecdd 100644 --- a/include/linux/ring_buffer.h +++ b/include/linux/ring_buffer.h @@ -125,7 +125,7 @@ ring_buffer_consume(struct ring_buffer *buffer, int cpu, u64 *ts, unsigned long *lost_events);
struct ring_buffer_iter * -ring_buffer_read_prepare(struct ring_buffer *buffer, int cpu); +ring_buffer_read_prepare(struct ring_buffer *buffer, int cpu, gfp_t flags); void ring_buffer_read_prepare_sync(void); void ring_buffer_read_start(struct ring_buffer_iter *iter); void ring_buffer_read_finish(struct ring_buffer_iter *iter); diff --git a/kernel/trace/ring_buffer.c b/kernel/trace/ring_buffer.c index f316e90ad538..5473dcaaca8d 100644 --- a/kernel/trace/ring_buffer.c +++ b/kernel/trace/ring_buffer.c @@ -4037,6 +4037,7 @@ EXPORT_SYMBOL_GPL(ring_buffer_consume); * ring_buffer_read_prepare - Prepare for a non consuming read of the buffer * @buffer: The ring buffer to read from * @cpu: The cpu buffer to iterate over + * @flags: gfp flags to use for memory allocation * * This performs the initial preparations necessary to iterate * through the buffer. Memory is allocated, buffer recording @@ -4054,7 +4055,7 @@ EXPORT_SYMBOL_GPL(ring_buffer_consume); * This overall must be paired with ring_buffer_read_finish. */ struct ring_buffer_iter * -ring_buffer_read_prepare(struct ring_buffer *buffer, int cpu) +ring_buffer_read_prepare(struct ring_buffer *buffer, int cpu, gfp_t flags) { struct ring_buffer_per_cpu *cpu_buffer; struct ring_buffer_iter *iter; @@ -4062,7 +4063,7 @@ ring_buffer_read_prepare(struct ring_buffer *buffer, int cpu) if (!cpumask_test_cpu(cpu, buffer->cpumask)) return NULL;
- iter = kmalloc(sizeof(*iter), GFP_KERNEL); + iter = kmalloc(sizeof(*iter), flags); if (!iter) return NULL;
diff --git a/kernel/trace/trace.c b/kernel/trace/trace.c index f18dedf9195e..d4773939c054 100644 --- a/kernel/trace/trace.c +++ b/kernel/trace/trace.c @@ -3449,7 +3449,8 @@ __tracing_open(struct inode *inode, struct file *file, bool snapshot) if (iter->cpu_file == RING_BUFFER_ALL_CPUS) { for_each_tracing_cpu(cpu) { iter->buffer_iter[cpu] = - ring_buffer_read_prepare(iter->trace_buffer->buffer, cpu); + ring_buffer_read_prepare(iter->trace_buffer->buffer, + cpu, GFP_KERNEL); } ring_buffer_read_prepare_sync(); for_each_tracing_cpu(cpu) { @@ -3459,7 +3460,8 @@ __tracing_open(struct inode *inode, struct file *file, bool snapshot) } else { cpu = iter->cpu_file; iter->buffer_iter[cpu] = - ring_buffer_read_prepare(iter->trace_buffer->buffer, cpu); + ring_buffer_read_prepare(iter->trace_buffer->buffer, + cpu, GFP_KERNEL); ring_buffer_read_prepare_sync(); ring_buffer_read_start(iter->buffer_iter[cpu]); tracing_iter_reset(iter, cpu); diff --git a/kernel/trace/trace_kdb.c b/kernel/trace/trace_kdb.c index 57149bce6aad..896458285fdd 100644 --- a/kernel/trace/trace_kdb.c +++ b/kernel/trace/trace_kdb.c @@ -50,14 +50,16 @@ static void ftrace_dump_buf(int skip_lines, long cpu_file) if (cpu_file == RING_BUFFER_ALL_CPUS) { for_each_tracing_cpu(cpu) { iter.buffer_iter[cpu] = - ring_buffer_read_prepare(iter.trace_buffer->buffer, cpu); + ring_buffer_read_prepare(iter.trace_buffer->buffer, + cpu, GFP_ATOMIC); ring_buffer_read_start(iter.buffer_iter[cpu]); tracing_iter_reset(&iter, cpu); } } else { iter.cpu_file = cpu_file; iter.buffer_iter[cpu_file] = - ring_buffer_read_prepare(iter.trace_buffer->buffer, cpu_file); + ring_buffer_read_prepare(iter.trace_buffer->buffer, + cpu_file, GFP_ATOMIC); ring_buffer_read_start(iter.buffer_iter[cpu_file]); tracing_iter_reset(&iter, cpu_file); }
From: Russell King rmk+kernel@armlinux.org.uk
[ Upstream commit d01849f7deba81f4959fd9e51bf20dbf46987d1c ]
Tony notes that the GPIO module does not idle when level interrupts are in use, as the wakeup appears to get stuck.
After extensive investigation, it appears that the wakeup will only be cleared if the interrupt status register is cleared while the interrupt is enabled. However, we are currently clearing it with the interrupt disabled for level-based interrupts.
It is acknowledged that this observed behaviour conflicts with a statement in the TRM:
CAUTION After servicing the interrupt, the status bit in the interrupt status register (GPIOi.GPIO_IRQSTATUS_0 or GPIOi.GPIO_IRQSTATUS_1) must be reset and the interrupt line released (by setting the corresponding bit of the interrupt status register to 1) before enabling an interrupt for the GPIO channel in the interrupt-enable register (GPIOi.GPIO_IRQSTATUS_SET_0 or GPIOi.GPIO_IRQSTATUS_SET_1) to prevent the occurrence of unexpected interrupts when enabling an interrupt for the GPIO channel.
However, this does not appear to be a practical problem.
Further, as reported by Grygorii Strashko grygorii.strashko@ti.com, the TI Android kernel tree has an earlier similar patch as "GPIO: OMAP: Fix the sequence to clear the IRQ status" saying:
if the status is cleared after disabling the IRQ then sWAKEUP will not be cleared and gates the module transition
When we unmask the level interrupt after the interrupt has been handled, enable the interrupt and only then clear the interrupt. If the interrupt is still pending, the hardware will re-assert the interrupt status.
Should the caution note in the TRM prove to be a problem, we could use a clear-enable-clear sequence instead.
Cc: Aaro Koskinen aaro.koskinen@iki.fi Cc: Keerthy j-keerthy@ti.com Cc: Peter Ujfalusi peter.ujfalusi@ti.com Signed-off-by: Russell King rmk+kernel@armlinux.org.uk [tony@atomide.com: updated comments based on an earlier TI patch] Signed-off-by: Tony Lindgren tony@atomide.com Acked-by: Grygorii Strashko grygorii.strashko@ti.com Signed-off-by: Linus Walleij linus.walleij@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpio/gpio-omap.c | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-)
diff --git a/drivers/gpio/gpio-omap.c b/drivers/gpio/gpio-omap.c index 6f9c9ac6ee70..75f30a0c418a 100644 --- a/drivers/gpio/gpio-omap.c +++ b/drivers/gpio/gpio-omap.c @@ -837,14 +837,16 @@ static void omap_gpio_unmask_irq(struct irq_data *d) if (trigger) omap_set_gpio_triggering(bank, offset, trigger);
- /* For level-triggered GPIOs, the clearing must be done after - * the HW source is cleared, thus after the handler has run */ - if (bank->level_mask & BIT(offset)) { - omap_set_gpio_irqenable(bank, offset, 0); + omap_set_gpio_irqenable(bank, offset, 1); + + /* + * For level-triggered GPIOs, clearing must be done after the source + * is cleared, thus after the handler has run. OMAP4 needs this done + * after enabing the interrupt to clear the wakeup status. + */ + if (bank->level_mask & BIT(offset)) omap_clear_gpio_irqstatus(bank, offset); - }
- omap_set_gpio_irqenable(bank, offset, 1); raw_spin_unlock_irqrestore(&bank->lock, flags); }
From: Luc Van Oostenryck luc.vanoostenryck@gmail.com
[ Upstream commit 62461ac2e5b6520b6d65fc6d7d7b4b8df4b848d8 ]
The percpu member of this structure is declared as: struct ... ** __percpu member; So its type is: __percpu pointer to pointer to struct ...
But looking at how it's used, its type should be: pointer to __percpu pointer to struct ... and it should thus be declared as: struct ... * __percpu *member;
So fix the placement of '__percpu' in the definition of this structures.
This silents a few Sparse's warnings like: warning: incorrect type in initializer (different address spaces) expected void const [noderef] asn:3 *__vpp_verify got struct sched_domain **
Link: http://lkml.kernel.org/r/20190118144902.79065-1-luc.vanoostenryck@gmail.com Fixes: 017c59c042d01 ("relay: Use per CPU constructs for the relay channel buffer pointers") Signed-off-by: Luc Van Oostenryck luc.vanoostenryck@gmail.com Cc: Jens Axboe axboe@suse.de Cc: Thomas Gleixner tglx@linutronix.de Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- include/linux/relay.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/include/linux/relay.h b/include/linux/relay.h index 68c1448e56bb..2560f8706408 100644 --- a/include/linux/relay.h +++ b/include/linux/relay.h @@ -65,7 +65,7 @@ struct rchan struct kref kref; /* channel refcount */ void *private_data; /* for user-defined data */ size_t last_toobig; /* tried to log event > subbuf size */ - struct rchan_buf ** __percpu buf; /* per-cpu channel buffers */ + struct rchan_buf * __percpu *buf; /* per-cpu channel buffers */ int is_global; /* One global buffer ? */ struct list_head list; /* for channel list */ struct dentry *parent; /* parent dentry passed to open */
From: Christian Brauner christian@brauner.io
[ Upstream commit 32a5ad9c22852e6bd9e74bdec5934ef9d1480bc5 ]
Currently, when writing
echo 18446744073709551616 > /proc/sys/fs/file-max
/proc/sys/fs/file-max will overflow and be set to 0. That quickly crashes the system.
This commit sets the max and min value for file-max. The max value is set to long int. Any higher value cannot currently be used as the percpu counters are long ints and not unsigned integers.
Note that the file-max value is ultimately parsed via __do_proc_doulongvec_minmax(). This function does not report error when min or max are exceeded. Which means if a value largen that long int is written userspace will not receive an error instead the old value will be kept. There is an argument to be made that this should be changed and __do_proc_doulongvec_minmax() should return an error when a dedicated min or max value are exceeded. However this has the potential to break userspace so let's defer this to an RFC patch.
Link: http://lkml.kernel.org/r/20190107222700.15954-3-christian@brauner.io Signed-off-by: Christian Brauner christian@brauner.io Acked-by: Kees Cook keescook@chromium.org Cc: Alexey Dobriyan adobriyan@gmail.com Cc: Al Viro viro@zeniv.linux.org.uk Cc: Dominik Brodowski linux@dominikbrodowski.net Cc: "Eric W. Biederman" ebiederm@xmission.com Cc: Joe Lawrence joe.lawrence@redhat.com Cc: Luis Chamberlain mcgrof@kernel.org Cc: Waiman Long longman@redhat.com [christian@brauner.io: v4] Link: http://lkml.kernel.org/r/20190210203943.8227-3-christian@brauner.io Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/sysctl.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/kernel/sysctl.c b/kernel/sysctl.c index efd340a510a9..5515d578095b 100644 --- a/kernel/sysctl.c +++ b/kernel/sysctl.c @@ -125,6 +125,7 @@ static int __maybe_unused one = 1; static int __maybe_unused two = 2; static int __maybe_unused four = 4; static unsigned long one_ul = 1; +static unsigned long long_max = LONG_MAX; static int one_hundred = 100; static int one_thousand = 1000; #ifdef CONFIG_PRINTK @@ -1682,6 +1683,8 @@ static struct ctl_table fs_table[] = { .maxlen = sizeof(files_stat.max_files), .mode = 0644, .proc_handler = proc_doulongvec_minmax, + .extra1 = &zero, + .extra2 = &long_max, }, { .procname = "nr_open",
From: Arnd Bergmann arnd@arndb.de
[ Upstream commit 43d281662fdb46750d49417559b71069f435298d ]
The enic driver relies on the CONFIG_CPUMASK_OFFSTACK feature to dynamically allocate a struct member, but this is normally intended for local variables.
Building with clang, I get a warning for a few locations that check the address of the cpumask_var_t:
drivers/net/ethernet/cisco/enic/enic_main.c:122:22: error: address of array 'enic->msix[i].affinity_mask' will always evaluate to 'true' [-Werror,-Wpointer-bool-conversion]
As far as I can tell, the code is still correct, as the truth value of the pointer is what we need in this configuration. To get rid of the warning, use cpumask_available() instead of checking the pointer directly.
Fixes: 322cf7e3a4e8 ("enic: assign affinity hint to interrupts") Signed-off-by: Arnd Bergmann arnd@arndb.de Reviewed-by: Nathan Chancellor natechancellor@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/cisco/enic/enic_main.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/net/ethernet/cisco/enic/enic_main.c b/drivers/net/ethernet/cisco/enic/enic_main.c index 89acf7bc4cf9..b73d9ba9496c 100644 --- a/drivers/net/ethernet/cisco/enic/enic_main.c +++ b/drivers/net/ethernet/cisco/enic/enic_main.c @@ -120,7 +120,7 @@ static void enic_init_affinity_hint(struct enic *enic)
for (i = 0; i < enic->intr_count; i++) { if (enic_is_err_intr(enic, i) || enic_is_notify_intr(enic, i) || - (enic->msix[i].affinity_mask && + (cpumask_available(enic->msix[i].affinity_mask) && !cpumask_empty(enic->msix[i].affinity_mask))) continue; if (zalloc_cpumask_var(&enic->msix[i].affinity_mask, @@ -149,7 +149,7 @@ static void enic_set_affinity_hint(struct enic *enic) for (i = 0; i < enic->intr_count; i++) { if (enic_is_err_intr(enic, i) || enic_is_notify_intr(enic, i) || - !enic->msix[i].affinity_mask || + !cpumask_available(enic->msix[i].affinity_mask) || cpumask_empty(enic->msix[i].affinity_mask)) continue; err = irq_set_affinity_hint(enic->msix_entry[i].vector, @@ -162,7 +162,7 @@ static void enic_set_affinity_hint(struct enic *enic) for (i = 0; i < enic->wq_count; i++) { int wq_intr = enic_msix_wq_intr(enic, i);
- if (enic->msix[wq_intr].affinity_mask && + if (cpumask_available(enic->msix[wq_intr].affinity_mask) && !cpumask_empty(enic->msix[wq_intr].affinity_mask)) netif_set_xps_queue(enic->netdev, enic->msix[wq_intr].affinity_mask,
From: John Garry john.garry@huawei.com
[ Upstream commit efdcad62e7b8a02fcccc5ccca57806dce1482ac8 ]
When the PHY comes down, we currently do not set the negotiated linkrate:
root@(none)$ pwd /sys/class/sas_phy/phy-0:0 root@(none)$ more enable 1 root@(none)$ more negotiated_linkrate 12.0 Gbit root@(none)$ echo 0 > enable root@(none)$ more negotiated_linkrate 12.0 Gbit root@(none)$
This patch fixes the driver code to set it properly when the PHY comes down.
If the PHY had been enabled, then set unknown; otherwise, flag as disabled.
The logical place to set the negotiated linkrate for this scenario is PHY down routine, which is called from the PHY down ISR.
However, it is not possible to know if the PHY comes down due to PHY disable or loss of link, as sas_phy.enabled member is not set until after the transport disable routine is complete, which races with the PHY down ISR.
As an imperfect solution, use sas_phy_data.enable as the flag to know if the PHY is down due to disable. It's imperfect, as sas_phy_data is internal to libsas.
I can't see another way without adding a new field to hisi_sas_phy and managing it, or changing SCSI SAS transport.
Signed-off-by: John Garry john.garry@huawei.com Signed-off-by: Martin K. Petersen martin.petersen@oracle.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/scsi/hisi_sas/hisi_sas_main.c | 10 ++++++++++ 1 file changed, 10 insertions(+)
diff --git a/drivers/scsi/hisi_sas/hisi_sas_main.c b/drivers/scsi/hisi_sas/hisi_sas_main.c index 2f872f784e10..5252dd5d3f4b 100644 --- a/drivers/scsi/hisi_sas/hisi_sas_main.c +++ b/drivers/scsi/hisi_sas/hisi_sas_main.c @@ -10,6 +10,7 @@ */
#include "hisi_sas.h" +#include "../libsas/sas_internal.h" #define DRV_NAME "hisi_sas"
#define DEV_IS_GONE(dev) \ @@ -1128,9 +1129,18 @@ static void hisi_sas_port_deformed(struct asd_sas_phy *sas_phy)
static void hisi_sas_phy_disconnected(struct hisi_sas_phy *phy) { + struct asd_sas_phy *sas_phy = &phy->sas_phy; + struct sas_phy *sphy = sas_phy->phy; + struct sas_phy_data *d = sphy->hostdata; + phy->phy_attached = 0; phy->phy_type = 0; phy->port = NULL; + + if (d->enable) + sphy->negotiated_linkrate = SAS_LINK_RATE_UNKNOWN; + else + sphy->negotiated_linkrate = SAS_PHY_DISABLED; }
void hisi_sas_phy_down(struct hisi_hba *hisi_hba, int phy_no, int rdy)
From: Peng Fan peng.fan@nxp.com
[ Upstream commit 0d3bd18a5efd66097ef58622b898d3139790aa9d ]
In case cma_init_reserved_mem failed, need to free the memblock allocated by memblock_reserve or memblock_alloc_range.
Quote Catalin's comments: https://lkml.org/lkml/2019/2/26/482
Kmemleak is supposed to work with the memblock_{alloc,free} pair and it ignores the memblock_reserve() as a memblock_alloc() implementation detail. It is, however, tolerant to memblock_free() being called on a sub-range or just a different range from a previous memblock_alloc(). So the original patch looks fine to me. FWIW:
Link: http://lkml.kernel.org/r/20190227144631.16708-1-peng.fan@nxp.com Signed-off-by: Peng Fan peng.fan@nxp.com Reviewed-by: Catalin Marinas catalin.marinas@arm.com Reviewed-by: Mike Rapoport rppt@linux.ibm.com Cc: Laura Abbott labbott@redhat.com Cc: Joonsoo Kim iamjoonsoo.kim@lge.com Cc: Michal Hocko mhocko@suse.com Cc: Vlastimil Babka vbabka@suse.cz Cc: Marek Szyprowski m.szyprowski@samsung.com Cc: Andrey Konovalov andreyknvl@google.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- mm/cma.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/mm/cma.c b/mm/cma.c index 397687fc51f9..b5d8847497a3 100644 --- a/mm/cma.c +++ b/mm/cma.c @@ -339,12 +339,14 @@ int __init cma_declare_contiguous(phys_addr_t base,
ret = cma_init_reserved_mem(base, size, order_per_bit, res_cma); if (ret) - goto err; + goto free_mem;
pr_info("Reserved %ld MiB at %pa\n", (unsigned long)size / SZ_1M, &base); return 0;
+free_mem: + memblock_free(base, size); err: pr_err("Failed to reserve %ld MiB\n", (unsigned long)size / SZ_1M); return ret;
From: Qian Cai cai@lca.pw
[ Upstream commit 0c81585499601acd1d0e1cbf424cabfaee60628c ]
After offlining a memory block, kmemleak scan will trigger a crash, as it encounters a page ext address that has already been freed during memory offlining. At the beginning in alloc_page_ext(), it calls kmemleak_alloc(), but it does not call kmemleak_free() in free_page_ext().
BUG: unable to handle kernel paging request at ffff888453d00000 PGD 128a01067 P4D 128a01067 PUD 128a04067 PMD 47e09e067 PTE 800ffffbac2ff060 Oops: 0000 [#1] SMP DEBUG_PAGEALLOC KASAN PTI CPU: 1 PID: 1594 Comm: bash Not tainted 5.0.0-rc8+ #15 Hardware name: HP ProLiant DL180 Gen9/ProLiant DL180 Gen9, BIOS U20 10/25/2017 RIP: 0010:scan_block+0xb5/0x290 Code: 85 6e 01 00 00 48 b8 00 00 30 f5 81 88 ff ff 48 39 c3 0f 84 5b 01 00 00 48 89 d8 48 c1 e8 03 42 80 3c 20 00 0f 85 87 01 00 00 <4c> 8b 3b e8 f3 0c fa ff 4c 39 3d 0c 6b 4c 01 0f 87 08 01 00 00 4c RSP: 0018:ffff8881ec57f8e0 EFLAGS: 00010082 RAX: 0000000000000000 RBX: ffff888453d00000 RCX: ffffffffa61e5a54 RDX: 0000000000000000 RSI: 0000000000000008 RDI: ffff888453d00000 RBP: ffff8881ec57f920 R08: fffffbfff4ed588d R09: fffffbfff4ed588c R10: fffffbfff4ed588c R11: ffffffffa76ac463 R12: dffffc0000000000 R13: ffff888453d00ff9 R14: ffff8881f80cef48 R15: ffff8881f80cef48 FS: 00007f6c0e3f8740(0000) GS:ffff8881f7680000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: ffff888453d00000 CR3: 00000001c4244003 CR4: 00000000001606a0 Call Trace: scan_gray_list+0x269/0x430 kmemleak_scan+0x5a8/0x10f0 kmemleak_write+0x541/0x6ca full_proxy_write+0xf8/0x190 __vfs_write+0xeb/0x980 vfs_write+0x15a/0x4f0 ksys_write+0xd2/0x1b0 __x64_sys_write+0x73/0xb0 do_syscall_64+0xeb/0xaaa entry_SYSCALL_64_after_hwframe+0x44/0xa9 RIP: 0033:0x7f6c0dad73b8 Code: 89 02 48 c7 c0 ff ff ff ff eb b3 0f 1f 80 00 00 00 00 f3 0f 1e fa 48 8d 05 65 63 2d 00 8b 00 85 c0 75 17 b8 01 00 00 00 0f 05 <48> 3d 00 f0 ff ff 77 58 c3 0f 1f 80 00 00 00 00 41 54 49 89 d4 55 RSP: 002b:00007ffd5b863cb8 EFLAGS: 00000246 ORIG_RAX: 0000000000000001 RAX: ffffffffffffffda RBX: 0000000000000005 RCX: 00007f6c0dad73b8 RDX: 0000000000000005 RSI: 000055a9216e1710 RDI: 0000000000000001 RBP: 000055a9216e1710 R08: 000000000000000a R09: 00007ffd5b863840 R10: 000000000000000a R11: 0000000000000246 R12: 00007f6c0dda9780 R13: 0000000000000005 R14: 00007f6c0dda4740 R15: 0000000000000005 Modules linked in: nls_iso8859_1 nls_cp437 vfat fat kvm_intel kvm irqbypass efivars ip_tables x_tables xfs sd_mod ahci libahci igb i2c_algo_bit libata i2c_core dm_mirror dm_region_hash dm_log dm_mod efivarfs CR2: ffff888453d00000 ---[ end trace ccf646c7456717c5 ]--- Kernel panic - not syncing: Fatal exception Shutting down cpus with NMI Kernel Offset: 0x24c00000 from 0xffffffff81000000 (relocation range: 0xffffffff80000000-0xffffffffbfffffff) ---[ end Kernel panic - not syncing: Fatal exception ]---
Link: http://lkml.kernel.org/r/20190227173147.75650-1-cai@lca.pw Signed-off-by: Qian Cai cai@lca.pw Reviewed-by: Catalin Marinas catalin.marinas@arm.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- mm/page_ext.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/mm/page_ext.c b/mm/page_ext.c index 121dcffc4ec1..a7be1c7a79f6 100644 --- a/mm/page_ext.c +++ b/mm/page_ext.c @@ -286,6 +286,7 @@ static void free_page_ext(void *addr) table_size = get_entry_size() * PAGES_PER_SECTION;
BUG_ON(PageReserved(page)); + kmemleak_free(addr); free_pages_exact(addr, table_size); } }
From: "Uladzislau Rezki (Sony)" urezki@gmail.com
[ Upstream commit afd07389d3f4933c7f7817a92fb5e053d59a3182 ]
One of the vmalloc stress test case triggers the kernel BUG():
<snip> [60.562151] ------------[ cut here ]------------ [60.562154] kernel BUG at mm/vmalloc.c:512! [60.562206] invalid opcode: 0000 [#1] PREEMPT SMP PTI [60.562247] CPU: 0 PID: 430 Comm: vmalloc_test/0 Not tainted 4.20.0+ #161 [60.562293] Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS 1.10.2-1 04/01/2014 [60.562351] RIP: 0010:alloc_vmap_area+0x36f/0x390 <snip>
it can happen due to big align request resulting in overflowing of calculated address, i.e. it becomes 0 after ALIGN()'s fixup.
Fix it by checking if calculated address is within vstart/vend range.
Link: http://lkml.kernel.org/r/20190124115648.9433-2-urezki@gmail.com Signed-off-by: Uladzislau Rezki (Sony) urezki@gmail.com Reviewed-by: Andrew Morton akpm@linux-foundation.org Cc: Ingo Molnar mingo@elte.hu Cc: Joel Fernandes joelaf@google.com Cc: Matthew Wilcox willy@infradead.org Cc: Michal Hocko mhocko@suse.com Cc: Oleksiy Avramchenko oleksiy.avramchenko@sonymobile.com Cc: Steven Rostedt rostedt@goodmis.org Cc: Tejun Heo tj@kernel.org Cc: Thomas Garnier thgarnie@google.com Cc: Thomas Gleixner tglx@linutronix.de Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- mm/vmalloc.c | 6 +++++- 1 file changed, 5 insertions(+), 1 deletion(-)
diff --git a/mm/vmalloc.c b/mm/vmalloc.c index e6aa073f01df..73afe460caf0 100644 --- a/mm/vmalloc.c +++ b/mm/vmalloc.c @@ -459,7 +459,11 @@ static struct vmap_area *alloc_vmap_area(unsigned long size, }
found: - if (addr + size > vend) + /* + * Check also calculated address against the vstart, + * because it can be 0 because of big align request. + */ + if (addr + size > vend || addr < vstart) goto overflow;
va->va_start = addr;
From: Qian Cai cai@lca.pw
[ Upstream commit 92d1d07daad65c300c7d0b68bbef8867e9895d54 ]
Kmemleak throws endless warnings during boot due to in __alloc_alien_cache(),
alc = kmalloc_node(memsize, gfp, node); init_arraycache(&alc->ac, entries, batch); kmemleak_no_scan(ac);
Kmemleak does not track the array cache (alc->ac) but the alien cache (alc) instead, so let it track the latter by lifting kmemleak_no_scan() out of init_arraycache().
There is another place that calls init_arraycache(), but alloc_kmem_cache_cpus() uses the percpu allocation where will never be considered as a leak.
kmemleak: Found object by alias at 0xffff8007b9aa7e38 CPU: 190 PID: 1 Comm: swapper/0 Not tainted 5.0.0-rc2+ #2 Call trace: dump_backtrace+0x0/0x168 show_stack+0x24/0x30 dump_stack+0x88/0xb0 lookup_object+0x84/0xac find_and_get_object+0x84/0xe4 kmemleak_no_scan+0x74/0xf4 setup_kmem_cache_node+0x2b4/0x35c __do_tune_cpucache+0x250/0x2d4 do_tune_cpucache+0x4c/0xe4 enable_cpucache+0xc8/0x110 setup_cpu_cache+0x40/0x1b8 __kmem_cache_create+0x240/0x358 create_cache+0xc0/0x198 kmem_cache_create_usercopy+0x158/0x20c kmem_cache_create+0x50/0x64 fsnotify_init+0x58/0x6c do_one_initcall+0x194/0x388 kernel_init_freeable+0x668/0x688 kernel_init+0x18/0x124 ret_from_fork+0x10/0x18 kmemleak: Object 0xffff8007b9aa7e00 (size 256): kmemleak: comm "swapper/0", pid 1, jiffies 4294697137 kmemleak: min_count = 1 kmemleak: count = 0 kmemleak: flags = 0x1 kmemleak: checksum = 0 kmemleak: backtrace: kmemleak_alloc+0x84/0xb8 kmem_cache_alloc_node_trace+0x31c/0x3a0 __kmalloc_node+0x58/0x78 setup_kmem_cache_node+0x26c/0x35c __do_tune_cpucache+0x250/0x2d4 do_tune_cpucache+0x4c/0xe4 enable_cpucache+0xc8/0x110 setup_cpu_cache+0x40/0x1b8 __kmem_cache_create+0x240/0x358 create_cache+0xc0/0x198 kmem_cache_create_usercopy+0x158/0x20c kmem_cache_create+0x50/0x64 fsnotify_init+0x58/0x6c do_one_initcall+0x194/0x388 kernel_init_freeable+0x668/0x688 kernel_init+0x18/0x124 kmemleak: Not scanning unknown object at 0xffff8007b9aa7e38 CPU: 190 PID: 1 Comm: swapper/0 Not tainted 5.0.0-rc2+ #2 Call trace: dump_backtrace+0x0/0x168 show_stack+0x24/0x30 dump_stack+0x88/0xb0 kmemleak_no_scan+0x90/0xf4 setup_kmem_cache_node+0x2b4/0x35c __do_tune_cpucache+0x250/0x2d4 do_tune_cpucache+0x4c/0xe4 enable_cpucache+0xc8/0x110 setup_cpu_cache+0x40/0x1b8 __kmem_cache_create+0x240/0x358 create_cache+0xc0/0x198 kmem_cache_create_usercopy+0x158/0x20c kmem_cache_create+0x50/0x64 fsnotify_init+0x58/0x6c do_one_initcall+0x194/0x388 kernel_init_freeable+0x668/0x688 kernel_init+0x18/0x124 ret_from_fork+0x10/0x18
Link: http://lkml.kernel.org/r/20190129184518.39808-1-cai@lca.pw Fixes: 1fe00d50a9e8 ("slab: factor out initialization of array cache") Signed-off-by: Qian Cai cai@lca.pw Reviewed-by: Andrew Morton akpm@linux-foundation.org Cc: Christoph Lameter cl@linux.com Cc: Pekka Enberg penberg@kernel.org Cc: David Rientjes rientjes@google.com Cc: Joonsoo Kim iamjoonsoo.kim@lge.com Cc: Catalin Marinas catalin.marinas@arm.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- mm/slab.c | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/mm/slab.c b/mm/slab.c index 354a09deecff..d2c0499c6b15 100644 --- a/mm/slab.c +++ b/mm/slab.c @@ -566,14 +566,6 @@ static void start_cpu_timer(int cpu)
static void init_arraycache(struct array_cache *ac, int limit, int batch) { - /* - * The array_cache structures contain pointers to free object. - * However, when such objects are allocated or transferred to another - * cache the pointers are not cleared and they could be counted as - * valid references during a kmemleak scan. Therefore, kmemleak must - * not scan such objects. - */ - kmemleak_no_scan(ac); if (ac) { ac->avail = 0; ac->limit = limit; @@ -589,6 +581,14 @@ static struct array_cache *alloc_arraycache(int node, int entries, struct array_cache *ac = NULL;
ac = kmalloc_node(memsize, gfp, node); + /* + * The array_cache structures contain pointers to free object. + * However, when such objects are allocated or transferred to another + * cache the pointers are not cleared and they could be counted as + * valid references during a kmemleak scan. Therefore, kmemleak must + * not scan such objects. + */ + kmemleak_no_scan(ac); init_arraycache(ac, entries, batchcount); return ac; } @@ -683,6 +683,7 @@ static struct alien_cache *__alloc_alien_cache(int node, int entries,
alc = kmalloc_node(memsize, gfp, node); if (alc) { + kmemleak_no_scan(alc); init_arraycache(&alc->ac, entries, batch); spin_lock_init(&alc->lock); }
From: Jia Guo guojia12@huawei.com
[ Upstream commit cc725ef3cb202ef2019a3c67c8913efa05c3cce6 ]
In the process of creating a node, it will cause NULL pointer dereference in kernel if o2cb_ctl failed in the interval (mkdir, o2cb_set_node_attribute(node_num)] in function o2cb_add_node.
The node num is initialized to 0 in function o2nm_node_group_make_item, o2nm_node_group_drop_item will mistake the node number 0 for a valid node number when we delete the node before the node number is set correctly. If the local node number of the current host happens to be 0, cluster->cl_local_node will be set to O2NM_INVALID_NODE_NUM while o2hb_thread still running. The panic stack is generated as follows:
o2hb_thread -o2hb_do_disk_heartbeat -o2hb_check_own_slot |-slot = ®->hr_slots[o2nm_this_node()]; //o2nm_this_node() return O2NM_INVALID_NODE_NUM
We need to check whether the node number is set when we delete the node.
Link: http://lkml.kernel.org/r/133d8045-72cc-863e-8eae-5013f9f6bc51@huawei.com Signed-off-by: Jia Guo guojia12@huawei.com Reviewed-by: Joseph Qi jiangqi903@gmail.com Acked-by: Jun Piao piaojun@huawei.com Cc: Mark Fasheh mark@fasheh.com Cc: Joel Becker jlbec@evilplan.org Cc: Junxiao Bi junxiao.bi@oracle.com Cc: Changwei Ge ge.changwei@h3c.com Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- fs/ocfs2/cluster/nodemanager.c | 14 ++++++++------ 1 file changed, 8 insertions(+), 6 deletions(-)
diff --git a/fs/ocfs2/cluster/nodemanager.c b/fs/ocfs2/cluster/nodemanager.c index c204ac9b49e5..81a0d5d82757 100644 --- a/fs/ocfs2/cluster/nodemanager.c +++ b/fs/ocfs2/cluster/nodemanager.c @@ -621,13 +621,15 @@ static void o2nm_node_group_drop_item(struct config_group *group, struct o2nm_node *node = to_o2nm_node(item); struct o2nm_cluster *cluster = to_o2nm_cluster(group->cg_item.ci_parent);
- o2net_disconnect_node(node); + if (cluster->cl_nodes[node->nd_num] == node) { + o2net_disconnect_node(node);
- if (cluster->cl_has_local && - (cluster->cl_local_node == node->nd_num)) { - cluster->cl_has_local = 0; - cluster->cl_local_node = O2NM_INVALID_NODE_NUM; - o2net_stop_listening(node); + if (cluster->cl_has_local && + (cluster->cl_local_node == node->nd_num)) { + cluster->cl_has_local = 0; + cluster->cl_local_node = O2NM_INVALID_NODE_NUM; + o2net_stop_listening(node); + } }
/* XXX call into net to stop this node from trading messages */
From: Sahitya Tummala stummala@codeaurora.org
[ Upstream commit 9083977dabf3833298ddcd40dee28687f1e6b483 ]
Fix below warning coming because of using mutex lock in atomic context.
BUG: sleeping function called from invalid context at kernel/locking/mutex.c:98 in_atomic(): 1, irqs_disabled(): 0, pid: 585, name: sh Preemption disabled at: __radix_tree_preload+0x28/0x130 Call trace: dump_backtrace+0x0/0x2b4 show_stack+0x20/0x28 dump_stack+0xa8/0xe0 ___might_sleep+0x144/0x194 __might_sleep+0x58/0x8c mutex_lock+0x2c/0x48 f2fs_trace_pid+0x88/0x14c f2fs_set_node_page_dirty+0xd0/0x184
Do not use f2fs_radix_tree_insert() to avoid doing cond_resched() with spin_lock() acquired.
Signed-off-by: Sahitya Tummala stummala@codeaurora.org Reviewed-by: Chao Yu yuchao0@huawei.com Signed-off-by: Jaegeuk Kim jaegeuk@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- fs/f2fs/trace.c | 8 +++++++- 1 file changed, 7 insertions(+), 1 deletion(-)
diff --git a/fs/f2fs/trace.c b/fs/f2fs/trace.c index 73b4e1d1912a..501c283761d2 100644 --- a/fs/f2fs/trace.c +++ b/fs/f2fs/trace.c @@ -61,6 +61,7 @@ void f2fs_trace_pid(struct page *page)
page->private = pid;
+retry: if (radix_tree_preload(GFP_NOFS)) return;
@@ -71,7 +72,12 @@ void f2fs_trace_pid(struct page *page) if (p) radix_tree_delete(&pids, pid);
- f2fs_radix_tree_insert(&pids, pid, current); + if (radix_tree_insert(&pids, pid, current)) { + spin_unlock(&pids_lock); + radix_tree_preload_end(); + cond_resched(); + goto retry; + }
trace_printk("%3x:%3x %4x %-16s\n", MAJOR(inode->i_sb->s_dev), MINOR(inode->i_sb->s_dev),
From: Shuriyc Chu sureeju@gmail.com
[ Upstream commit 5704a06810682683355624923547b41540e2801a ]
(Taken from https://bugzilla.kernel.org/show_bug.cgi?id=200647)
'get_unused_fd_flags' in kthread cause kernel crash. It works fine on 4.1, but causes crash after get 64 fds. It also cause crash on ubuntu1404/1604/1804, centos7.5, and the crash messages are almost the same.
The crash message on centos7.5 shows below:
start fd 61 start fd 62 start fd 63 BUG: unable to handle kernel NULL pointer dereference at (null) IP: __wake_up_common+0x2e/0x90 PGD 0 Oops: 0000 [#1] SMP Modules linked in: test(OE) xt_CHECKSUM iptable_mangle ipt_MASQUERADE nf_nat_masquerade_ipv4 iptable_nat nf_nat_ipv4 nf_nat nf_conntrack_ipv4 nf_defrag_ipv4 xt_conntrack nf_conntrack ipt_REJECT nf_reject_ipv4 tun bridge stp llc ebtable_filter ebtables ip6table_filter ip6_tables iptable_filter devlink sunrpc kvm_intel kvm irqbypass crc32_pclmul ghash_clmulni_intel aesni_intel lrw gf128mul glue_helper ablk_helper cryptd sg ppdev pcspkr virtio_balloon parport_pc parport i2c_piix4 joydev ip_tables xfs libcrc32c sr_mod cdrom sd_mod crc_t10dif crct10dif_generic ata_generic pata_acpi virtio_scsi virtio_console virtio_net cirrus drm_kms_helper syscopyarea sysfillrect sysimgblt fb_sys_fops ttm crct10dif_pclmul crct10dif_common crc32c_intel drm ata_piix serio_raw libata virtio_pci virtio_ring i2c_core virtio floppy dm_mirror dm_region_hash dm_log dm_mod CPU: 2 PID: 1820 Comm: test_fd Kdump: loaded Tainted: G OE ------------ 3.10.0-862.3.3.el7.x86_64 #1 Hardware name: QEMU Standard PC (i440FX + PIIX, 1996), BIOS rel-1.10.2-0-g5f4c7b1-prebuilt.qemu-project.org 04/01/2014 task: ffff8e92b9431fa0 ti: ffff8e94247a0000 task.ti: ffff8e94247a0000 RIP: 0010:__wake_up_common+0x2e/0x90 RSP: 0018:ffff8e94247a2d18 EFLAGS: 00010086 RAX: 0000000000000000 RBX: ffffffff9d09daa0 RCX: 0000000000000000 RDX: 0000000000000000 RSI: 0000000000000003 RDI: ffffffff9d09daa0 RBP: ffff8e94247a2d50 R08: 0000000000000000 R09: ffff8e92b95dfda8 R10: 0000000000000000 R11: 0000000000000000 R12: ffffffff9d09daa8 R13: 0000000000000003 R14: 0000000000000000 R15: 0000000000000003 FS: 0000000000000000(0000) GS:ffff8e9434e80000(0000) knlGS:0000000000000000 CS: 0010 DS: 0000 ES: 0000 CR0: 0000000080050033 CR2: 0000000000000000 CR3: 000000017c686000 CR4: 00000000000207e0 Call Trace: __wake_up+0x39/0x50 expand_files+0x131/0x250 __alloc_fd+0x47/0x170 get_unused_fd_flags+0x30/0x40 test_fd+0x12a/0x1c0 [test] kthread+0xd1/0xe0 ret_from_fork_nospec_begin+0x21/0x21 Code: 66 90 55 48 89 e5 41 57 41 89 f7 41 56 41 89 ce 41 55 41 54 49 89 fc 49 83 c4 08 53 48 83 ec 10 48 8b 47 08 89 55 cc 4c 89 45 d0 <48> 8b 08 49 39 c4 48 8d 78 e8 4c 8d 69 e8 75 08 eb 3b 4c 89 ef RIP __wake_up_common+0x2e/0x90 RSP <ffff8e94247a2d18> CR2: 0000000000000000
This issue exists since CentOS 7.5 3.10.0-862 and CentOS 7.4 (3.10.0-693.21.1 ) is ok. Root cause: the item 'resize_wait' is not initialized before being used.
Reported-by: Richard Zhang zhang.zijian@h3c.com Reviewed-by: Andrew Morton akpm@linux-foundation.org Cc: Al Viro viro@zeniv.linux.org.uk Signed-off-by: Andrew Morton akpm@linux-foundation.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- fs/file.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/fs/file.c b/fs/file.c index 69d6990e3021..09aac4d4729b 100644 --- a/fs/file.c +++ b/fs/file.c @@ -475,6 +475,7 @@ struct files_struct init_files = { .full_fds_bits = init_files.full_fds_bits_init, }, .file_lock = __SPIN_LOCK_UNLOCKED(init_files.file_lock), + .resize_wait = __WAIT_QUEUE_HEAD_INITIALIZER(init_files.resize_wait), };
static unsigned int find_next_fd(struct fdtable *fdt, unsigned int start)
From: Louis Taylor louis@kragniz.eu
[ Upstream commit 259594bea574e515a148171b5cd84ce5cbdc028a ]
When compiling with -Wformat, clang emits the following warnings:
fs/cifs/smb1ops.c:312:20: warning: format specifies type 'unsigned short' but the argument has type 'unsigned int' [-Wformat] tgt_total_cnt, total_in_tgt); ^~~~~~~~~~~~
fs/cifs/cifs_dfs_ref.c:289:4: warning: format specifies type 'short' but the argument has type 'int' [-Wformat] ref->flags, ref->server_type); ^~~~~~~~~~
fs/cifs/cifs_dfs_ref.c:289:16: warning: format specifies type 'short' but the argument has type 'int' [-Wformat] ref->flags, ref->server_type); ^~~~~~~~~~~~~~~~
fs/cifs/cifs_dfs_ref.c:291:4: warning: format specifies type 'short' but the argument has type 'int' [-Wformat] ref->ref_flag, ref->path_consumed); ^~~~~~~~~~~~~
fs/cifs/cifs_dfs_ref.c:291:19: warning: format specifies type 'short' but the argument has type 'int' [-Wformat] ref->ref_flag, ref->path_consumed); ^~~~~~~~~~~~~~~~~~ The types of these arguments are unconditionally defined, so this patch updates the format character to the correct ones for ints and unsigned ints.
Link: https://github.com/ClangBuiltLinux/linux/issues/378
Signed-off-by: Louis Taylor louis@kragniz.eu Signed-off-by: Steve French stfrench@microsoft.com Reviewed-by: Nick Desaulniers ndesaulniers@google.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/cifs/cifs_dfs_ref.c | 4 ++-- fs/cifs/smb1ops.c | 2 +- 2 files changed, 3 insertions(+), 3 deletions(-)
diff --git a/fs/cifs/cifs_dfs_ref.c b/fs/cifs/cifs_dfs_ref.c index 9156be545b0f..4660208132a2 100644 --- a/fs/cifs/cifs_dfs_ref.c +++ b/fs/cifs/cifs_dfs_ref.c @@ -271,9 +271,9 @@ static void dump_referral(const struct dfs_info3_param *ref) { cifs_dbg(FYI, "DFS: ref path: %s\n", ref->path_name); cifs_dbg(FYI, "DFS: node path: %s\n", ref->node_name); - cifs_dbg(FYI, "DFS: fl: %hd, srv_type: %hd\n", + cifs_dbg(FYI, "DFS: fl: %d, srv_type: %d\n", ref->flags, ref->server_type); - cifs_dbg(FYI, "DFS: ref_flags: %hd, path_consumed: %hd\n", + cifs_dbg(FYI, "DFS: ref_flags: %d, path_consumed: %d\n", ref->ref_flag, ref->path_consumed); }
diff --git a/fs/cifs/smb1ops.c b/fs/cifs/smb1ops.c index efd72e1fae74..f7a9adab0b84 100644 --- a/fs/cifs/smb1ops.c +++ b/fs/cifs/smb1ops.c @@ -305,7 +305,7 @@ coalesce_t2(char *second_buf, struct smb_hdr *target_hdr) remaining = tgt_total_cnt - total_in_tgt;
if (remaining < 0) { - cifs_dbg(FYI, "Server sent too much data. tgt_total_cnt=%hu total_in_tgt=%hu\n", + cifs_dbg(FYI, "Server sent too much data. tgt_total_cnt=%hu total_in_tgt=%u\n", tgt_total_cnt, total_in_tgt); return -EPROTO; }
From: "Jason Cai (Xiang Feng)" jason.cai.kern@gmail.com
[ Upstream commit 70de2cbda8a5d788284469e755f8b097d339c240 ]
Invoking dm_get_device() twice on the same device path with different modes is dangerous. Because in that case, upgrade_mode() will alloc a new 'dm_dev' and free the old one, which may be referenced by a previous caller. Dereferencing the dangling pointer will trigger kernel NULL pointer dereference.
The following two cases can reproduce this issue. Actually, they are invalid setups that must be disallowed, e.g.:
1. Creating a thin-pool with read_only mode, and the same device as both metadata and data.
dmsetup create thinp --table \ "0 41943040 thin-pool /dev/vdb /dev/vdb 128 0 1 read_only"
BUG: unable to handle kernel NULL pointer dereference at 0000000000000080 ... Call Trace: new_read+0xfb/0x110 [dm_bufio] dm_bm_read_lock+0x43/0x190 [dm_persistent_data] ? kmem_cache_alloc_trace+0x15c/0x1e0 __create_persistent_data_objects+0x65/0x3e0 [dm_thin_pool] dm_pool_metadata_open+0x8c/0xf0 [dm_thin_pool] pool_ctr.cold.79+0x213/0x913 [dm_thin_pool] ? realloc_argv+0x50/0x70 [dm_mod] dm_table_add_target+0x14e/0x330 [dm_mod] table_load+0x122/0x2e0 [dm_mod] ? dev_status+0x40/0x40 [dm_mod] ctl_ioctl+0x1aa/0x3e0 [dm_mod] dm_ctl_ioctl+0xa/0x10 [dm_mod] do_vfs_ioctl+0xa2/0x600 ? handle_mm_fault+0xda/0x200 ? __do_page_fault+0x26c/0x4f0 ksys_ioctl+0x60/0x90 __x64_sys_ioctl+0x16/0x20 do_syscall_64+0x55/0x150 entry_SYSCALL_64_after_hwframe+0x44/0xa9
2. Creating a external snapshot using the same thin-pool device.
dmsetup create thinp --table \ "0 41943040 thin-pool /dev/vdc /dev/vdb 128 0 2 ignore_discard" dmsetup message /dev/mapper/thinp 0 "create_thin 0" dmsetup create snap --table \ "0 204800 thin /dev/mapper/thinp 0 /dev/mapper/thinp"
BUG: unable to handle kernel NULL pointer dereference at 0000000000000000 ... Call Trace: ? __alloc_pages_nodemask+0x13c/0x2e0 retrieve_status+0xa5/0x1f0 [dm_mod] ? dm_get_live_or_inactive_table.isra.7+0x20/0x20 [dm_mod] table_status+0x61/0xa0 [dm_mod] ctl_ioctl+0x1aa/0x3e0 [dm_mod] dm_ctl_ioctl+0xa/0x10 [dm_mod] do_vfs_ioctl+0xa2/0x600 ksys_ioctl+0x60/0x90 ? ksys_write+0x4f/0xb0 __x64_sys_ioctl+0x16/0x20 do_syscall_64+0x55/0x150 entry_SYSCALL_64_after_hwframe+0x44/0xa9
Signed-off-by: Jason Cai (Xiang Feng) jason.cai@linux.alibaba.com Signed-off-by: Mike Snitzer snitzer@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/md/dm-thin.c | 13 +++++++++++++ 1 file changed, 13 insertions(+)
diff --git a/drivers/md/dm-thin.c b/drivers/md/dm-thin.c index 345f4d81ba07..23a7e108352a 100644 --- a/drivers/md/dm-thin.c +++ b/drivers/md/dm-thin.c @@ -3295,6 +3295,13 @@ static int pool_ctr(struct dm_target *ti, unsigned argc, char **argv) as.argc = argc; as.argv = argv;
+ /* make sure metadata and data are different devices */ + if (!strcmp(argv[0], argv[1])) { + ti->error = "Error setting metadata or data device"; + r = -EINVAL; + goto out_unlock; + } + /* * Set default pool features. */ @@ -4177,6 +4184,12 @@ static int thin_ctr(struct dm_target *ti, unsigned argc, char **argv) tc->sort_bio_list = RB_ROOT;
if (argc == 3) { + if (!strcmp(argv[0], argv[2])) { + ti->error = "Error setting origin device"; + r = -EINVAL; + goto bad_origin_dev; + } + r = dm_get_device(ti, argv[2], FMODE_READ, &origin_dev); if (r) { ti->error = "Error opening origin device";
From: Yao Liu yotta.liu@ucloud.cn
[ Upstream commit 68e2672f8fbd1e04982b8d2798dd318bf2515dd2 ]
There is a NULL pointer dereference of devname in strspn()
The oops looks something like:
CIFS: Attempting to mount (null) BUG: unable to handle kernel NULL pointer dereference at 0000000000000000 ... RIP: 0010:strspn+0x0/0x50 ... Call Trace: ? cifs_parse_mount_options+0x222/0x1710 [cifs] ? cifs_get_volume_info+0x2f/0x80 [cifs] cifs_setup_volume_info+0x20/0x190 [cifs] cifs_get_volume_info+0x50/0x80 [cifs] cifs_smb3_do_mount+0x59/0x630 [cifs] ? ida_alloc_range+0x34b/0x3d0 cifs_do_mount+0x11/0x20 [cifs] mount_fs+0x52/0x170 vfs_kern_mount+0x6b/0x170 do_mount+0x216/0xdc0 ksys_mount+0x83/0xd0 __x64_sys_mount+0x25/0x30 do_syscall_64+0x65/0x220 entry_SYSCALL_64_after_hwframe+0x49/0xbe
Fix this by adding a NULL check on devname in cifs_parse_devname()
Signed-off-by: Yao Liu yotta.liu@ucloud.cn Signed-off-by: Steve French stfrench@microsoft.com Signed-off-by: Sasha Levin sashal@kernel.org --- fs/cifs/connect.c | 5 +++++ 1 file changed, 5 insertions(+)
diff --git a/fs/cifs/connect.c b/fs/cifs/connect.c index 33e65b71c49a..f291ed0c155d 100644 --- a/fs/cifs/connect.c +++ b/fs/cifs/connect.c @@ -1201,6 +1201,11 @@ cifs_parse_devname(const char *devname, struct smb_vol *vol) const char *delims = "/\"; size_t len;
+ if (unlikely(!devname || !*devname)) { + cifs_dbg(VFS, "Device name not specified.\n"); + return -EINVAL; + } + /* make sure we have a valid UNC double delimiter prefix */ len = strspn(devname, delims); if (len != 2)
From: Slavomir Kaslev kaslevs@vmware.com
[ Upstream commit ee5e001196d1345b8fee25925ff5f1d67936081e ]
The current implementation of splice() and tee() ignores O_NONBLOCK set on pipe file descriptors and checks only the SPLICE_F_NONBLOCK flag for blocking on pipe arguments. This is inconsistent since splice()-ing from/to non-pipe file descriptors does take O_NONBLOCK into consideration.
Fix this by promoting O_NONBLOCK, when set on a pipe, to SPLICE_F_NONBLOCK.
Some context for how the current implementation of splice() leads to inconsistent behavior. In the ongoing work[1] to add VM tracing capability to trace-cmd we stream tracing data over named FIFOs or vsockets from guests back to the host.
When we receive SIGINT from user to stop tracing, we set O_NONBLOCK on the input file descriptor and set SPLICE_F_NONBLOCK for the next call to splice(). If splice() was blocked waiting on data from the input FIFO, after SIGINT splice() restarts with the same arguments (no SPLICE_F_NONBLOCK) and blocks again instead of returning -EAGAIN when no data is available.
This differs from the splice() behavior when reading from a vsocket or when we're doing a traditional read()/write() loop (trace-cmd's --nosplice argument).
With this patch applied we get the same behavior in all situations after setting O_NONBLOCK which also matches the behavior of doing a read()/write() loop instead of splice().
This change does have potential of breaking users who don't expect EAGAIN from splice() when SPLICE_F_NONBLOCK is not set. OTOH programs that set O_NONBLOCK and don't anticipate EAGAIN are arguably buggy[2].
[1] https://github.com/skaslev/trace-cmd/tree/vsock [2] https://github.com/torvalds/linux/blob/d47e3da1759230e394096fd742aad423c291b...
Signed-off-by: Slavomir Kaslev kaslevs@vmware.com Reviewed-by: Steven Rostedt (VMware) rostedt@goodmis.org Signed-off-by: Linus Torvalds torvalds@linux-foundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- fs/splice.c | 12 ++++++++++++ 1 file changed, 12 insertions(+)
diff --git a/fs/splice.c b/fs/splice.c index 01983bea760c..3f9e7a724d85 100644 --- a/fs/splice.c +++ b/fs/splice.c @@ -1137,6 +1137,9 @@ static long do_splice(struct file *in, loff_t __user *off_in, if (ipipe == opipe) return -EINVAL;
+ if ((in->f_flags | out->f_flags) & O_NONBLOCK) + flags |= SPLICE_F_NONBLOCK; + return splice_pipe_to_pipe(ipipe, opipe, len, flags); }
@@ -1162,6 +1165,9 @@ static long do_splice(struct file *in, loff_t __user *off_in, if (unlikely(ret < 0)) return ret;
+ if (in->f_flags & O_NONBLOCK) + flags |= SPLICE_F_NONBLOCK; + file_start_write(out); ret = do_splice_from(ipipe, out, &offset, len, flags); file_end_write(out); @@ -1186,6 +1192,9 @@ static long do_splice(struct file *in, loff_t __user *off_in, offset = in->f_pos; }
+ if (out->f_flags & O_NONBLOCK) + flags |= SPLICE_F_NONBLOCK; + pipe_lock(opipe); ret = wait_for_space(opipe, flags); if (!ret) @@ -1718,6 +1727,9 @@ static long do_tee(struct file *in, struct file *out, size_t len, * copying the data. */ if (ipipe && opipe && ipipe != opipe) { + if ((in->f_flags | out->f_flags) & O_NONBLOCK) + flags |= SPLICE_F_NONBLOCK; + /* * Keep going, unless we encounter an error. The ipipe/opipe * ordering doesn't really matter.
On Wed, 2019-03-27 at 14:19 -0400, Sasha Levin wrote:
From: Slavomir Kaslev kaslevs@vmware.com
[ Upstream commit ee5e001196d1345b8fee25925ff5f1d67936081e ]
The current implementation of splice() and tee() ignores O_NONBLOCK set on pipe file descriptors and checks only the SPLICE_F_NONBLOCK flag for blocking on pipe arguments. This is inconsistent since splice()-ing from/to non-pipe file descriptors does take O_NONBLOCK into consideration.
Fix this by promoting O_NONBLOCK, when set on a pipe, to SPLICE_F_NONBLOCK.
Hey Sasha,
I don't think that this patch should be merged to stable kernels. It's more of a feature rather than a bug/regression fix and it changes how splice() has been working from day one.
Can you please drop it from the stable queues?
Thanks,
-- Slavi
On Thu, 28 Mar 2019 15:37:49 +0000 Slavomir Kaslev kaslevs@vmware.com wrote:
On Wed, 2019-03-27 at 14:19 -0400, Sasha Levin wrote:
From: Slavomir Kaslev kaslevs@vmware.com
[ Upstream commit ee5e001196d1345b8fee25925ff5f1d67936081e ]
The current implementation of splice() and tee() ignores O_NONBLOCK set on pipe file descriptors and checks only the SPLICE_F_NONBLOCK flag for blocking on pipe arguments. This is inconsistent since splice()-ing from/to non-pipe file descriptors does take O_NONBLOCK into consideration.
Fix this by promoting O_NONBLOCK, when set on a pipe, to SPLICE_F_NONBLOCK.
Hey Sasha,
I don't think that this patch should be merged to stable kernels. It's more of a feature rather than a bug/regression fix and it changes how splice() has been working from day one.
Can you please drop it from the stable queues?
On the other hand, it keeps stable more in sync with what mainline has. If someone writes new code against a stable release, and depends on this behavior, it's less likely to break when they run it on a newer kernel. Which means its less likely that Linus will revert your change ;-)
-- Steve
On Thu, Mar 28, 2019 at 12:04:17PM -0400, Steven Rostedt wrote:
On Thu, 28 Mar 2019 15:37:49 +0000 Slavomir Kaslev kaslevs@vmware.com wrote:
On Wed, 2019-03-27 at 14:19 -0400, Sasha Levin wrote:
From: Slavomir Kaslev kaslevs@vmware.com
[ Upstream commit ee5e001196d1345b8fee25925ff5f1d67936081e ]
The current implementation of splice() and tee() ignores O_NONBLOCK set on pipe file descriptors and checks only the SPLICE_F_NONBLOCK flag for blocking on pipe arguments. This is inconsistent since splice()-ing from/to non-pipe file descriptors does take O_NONBLOCK into consideration.
Fix this by promoting O_NONBLOCK, when set on a pipe, to SPLICE_F_NONBLOCK.
Hey Sasha,
I don't think that this patch should be merged to stable kernels. It's more of a feature rather than a bug/regression fix and it changes how splice() has been working from day one.
Can you please drop it from the stable queues?
On the other hand, it keeps stable more in sync with what mainline has. If someone writes new code against a stable release, and depends on this behavior, it's less likely to break when they run it on a newer kernel. Which means its less likely that Linus will revert your change ;-)
I'm going to drop this, I don't really want to take things which knowingly might brake userspace.
-- Thanks, Sasha
From: luojiajun luojiajun3@huawei.com
[ Upstream commit 6e876c3dd205d30b0db6850e97a03d75457df007 ]
In jbd2_journal_commit_transaction(), if we are in abort mode, we may flush the buffer without setting descriptor block checksum by goto start_journal_io. Then fs is mounted, jbd2_descriptor_block_csum_verify() failed.
[ 271.379811] EXT4-fs (vdd): shut down requested (2) [ 271.381827] Aborting journal on device vdd-8. [ 271.597136] JBD2: Invalid checksum recovering block 22199 in log [ 271.598023] JBD2: recovery failed [ 271.598484] EXT4-fs (vdd): error loading journal
Fix this problem by keep setting descriptor block checksum if the descriptor buffer is not NULL.
This checksum problem can be reproduced by xfstests generic/388.
Signed-off-by: luojiajun luojiajun3@huawei.com Signed-off-by: Theodore Ts'o tytso@mit.edu Reviewed-by: Jan Kara jack@suse.cz Signed-off-by: Sasha Levin sashal@kernel.org --- fs/jbd2/commit.c | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-)
diff --git a/fs/jbd2/commit.c b/fs/jbd2/commit.c index 31f8ca046639..10ec27676191 100644 --- a/fs/jbd2/commit.c +++ b/fs/jbd2/commit.c @@ -700,9 +700,11 @@ void jbd2_journal_commit_transaction(journal_t *journal) the last tag we set up. */
tag->t_flags |= cpu_to_be16(JBD2_FLAG_LAST_TAG); - - jbd2_descriptor_block_csum_set(journal, descriptor); start_journal_io: + if (descriptor) + jbd2_descriptor_block_csum_set(journal, + descriptor); + for (i = 0; i < bufs; i++) { struct buffer_head *bh = wbuf[i]; /*
From: Carlos Maiolino cmaiolino@redhat.com
[ Upstream commit dce30ca9e3b676fb288c33c1f4725a0621361185 ]
guard_bio_eod() can truncate a segment in bio to allow it to do IO on odd last sectors of a device.
It already checks if the IO starts past EOD, but it does not consider the possibility of an IO request starting within device boundaries can contain more than one segment past EOD.
In such cases, truncated_bytes can be bigger than PAGE_SIZE, and will underflow bvec->bv_len.
Fix this by checking if truncated_bytes is lower than PAGE_SIZE.
This situation has been found on filesystems such as isofs and vfat, which doesn't check the device size before mount, if the device is smaller than the filesystem itself, a readahead on such filesystem, which spans EOD, can trigger this situation, leading a call to zero_user() with a wrong size possibly corrupting memory.
I didn't see any crash, or didn't let the system run long enough to check if memory corruption will be hit somewhere, but adding instrumentation to guard_bio_end() to check truncated_bytes size, was enough to see the error.
The following script can trigger the error.
MNT=/mnt IMG=./DISK.img DEV=/dev/loop0
mkfs.vfat $IMG mount $IMG $MNT cp -R /etc $MNT &> /dev/null umount $MNT
losetup -D
losetup --find --show --sizelimit 16247280 $IMG mount $DEV $MNT
find $MNT -type f -exec cat {} + >/dev/null
Kudos to Eric Sandeen for coming up with the reproducer above
Reviewed-by: Ming Lei ming.lei@redhat.com Signed-off-by: Carlos Maiolino cmaiolino@redhat.com Signed-off-by: Jens Axboe axboe@kernel.dk Signed-off-by: Sasha Levin sashal@kernel.org --- fs/buffer.c | 7 +++++++ 1 file changed, 7 insertions(+)
diff --git a/fs/buffer.c b/fs/buffer.c index e0d46d47e358..a89be9741d12 100644 --- a/fs/buffer.c +++ b/fs/buffer.c @@ -3041,6 +3041,13 @@ void guard_bio_eod(int op, struct bio *bio) /* Uhhuh. We've got a bio that straddles the device size! */ truncated_bytes = bio->bi_iter.bi_size - (maxsector << 9);
+ /* + * The bio contains more than one segment which spans EOD, just return + * and let IO layer turn it into an EIO + */ + if (truncated_bytes > bvec->bv_len) + return; + /* Truncate the bio.. */ bio->bi_iter.bi_size -= truncated_bytes; bvec->bv_len -= truncated_bytes;
From: Tony Jones tonyj@suse.de
[ Upstream commit 7c5b019e3a638a5a290b0ec020f6ca83d2ec2aaa ]
Fix buffer overflow observed when running perf test.
The overflow is when trying to evaluate "1ULL << (64 - 1)" which is resulting in -9223372036854775808 which overflows the 20 character buffer.
If is possible this bug has been reported before but I still don't see any fix checked in:
See: https://www.spinics.net/lists/linux-perf-users/msg07714.html
Reported-by: Michael Sartain mikesart@fastmail.com Reported-by: Mathias Krause minipli@googlemail.com Signed-off-by: Tony Jones tonyj@suse.de Acked-by: Steven Rostedt (VMware) rostedt@goodmis.org Cc: Frederic Weisbecker fweisbec@gmail.com Fixes: f7d82350e597 ("tools/events: Add files to create libtraceevent.a") Link: http://lkml.kernel.org/r/20190228015532.8941-1-tonyj@suse.de Signed-off-by: Arnaldo Carvalho de Melo acme@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- tools/lib/traceevent/event-parse.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/tools/lib/traceevent/event-parse.c b/tools/lib/traceevent/event-parse.c index 669475300ba8..700c74b0aed0 100644 --- a/tools/lib/traceevent/event-parse.c +++ b/tools/lib/traceevent/event-parse.c @@ -2428,7 +2428,7 @@ static int arg_num_eval(struct print_arg *arg, long long *val) static char *arg_eval (struct print_arg *arg) { long long val; - static char buf[20]; + static char buf[24];
switch (arg->type) { case PRINT_ATOM:
From: Alexei Avshalom Lazar ailizaro@codeaurora.org
[ Upstream commit de77a53c2d1e8fb3621e63e8e1f0f0c9a1a99ff7 ]
ies1 or ies2 might be null when code inside _wil_cfg80211_merge_extra_ies access them. Add explicit check for null and make sure ies1/ies2 are not accessed in such a case.
spos might be null and be accessed inside _wil_cfg80211_merge_extra_ies. Add explicit check for null in the while condition statement and make sure spos is not accessed in such a case.
Signed-off-by: Alexei Avshalom Lazar ailizaro@codeaurora.org Signed-off-by: Maya Erez merez@codeaurora.org Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ath/wil6210/cfg80211.c | 14 +++++++++++--- 1 file changed, 11 insertions(+), 3 deletions(-)
diff --git a/drivers/net/wireless/ath/wil6210/cfg80211.c b/drivers/net/wireless/ath/wil6210/cfg80211.c index d117240d9a73..b8eeaef17edc 100644 --- a/drivers/net/wireless/ath/wil6210/cfg80211.c +++ b/drivers/net/wireless/ath/wil6210/cfg80211.c @@ -1005,6 +1005,12 @@ static int _wil_cfg80211_merge_extra_ies(const u8 *ies1, u16 ies1_len, u8 *buf, *dpos; const u8 *spos;
+ if (!ies1) + ies1_len = 0; + + if (!ies2) + ies2_len = 0; + if (ies1_len == 0 && ies2_len == 0) { *merged_ies = NULL; *merged_len = 0; @@ -1014,17 +1020,19 @@ static int _wil_cfg80211_merge_extra_ies(const u8 *ies1, u16 ies1_len, buf = kmalloc(ies1_len + ies2_len, GFP_KERNEL); if (!buf) return -ENOMEM; - memcpy(buf, ies1, ies1_len); + if (ies1) + memcpy(buf, ies1, ies1_len); dpos = buf + ies1_len; spos = ies2; - while (spos + 1 < ies2 + ies2_len) { + while (spos && (spos + 1 < ies2 + ies2_len)) { /* IE tag at offset 0, length at offset 1 */ u16 ielen = 2 + spos[1];
if (spos + ielen > ies2 + ies2_len) break; if (spos[0] == WLAN_EID_VENDOR_SPECIFIC && - !_wil_cfg80211_find_ie(ies1, ies1_len, spos, ielen)) { + (!ies1 || !_wil_cfg80211_find_ie(ies1, ies1_len, + spos, ielen))) { memcpy(dpos, spos, ielen); dpos += ielen; }
From: Julia Lawall Julia.Lawall@lip6.fr
[ Upstream commit 8c2b43d2d85b48a97d2f8279278a4aac5b45f925 ]
Add an of_node_put when a tested device node is not available.
The semantic patch that fixes this problem is as follows (http://coccinelle.lip6.fr):
// <smpl> @@ identifier f; local idexpression e; expression x; @@
e = f(...); ... when != of_node_put(e) when != x = e when != e = x when any if (<+...of_device_is_available(e)...+>) { ... when != of_node_put(e) ( return e; | + of_node_put(e); return ...; ) } // </smpl>
Fixes: 5343e674f32fb ("crypto4xx: integrate ppc4xx-rng into crypto4xx") Signed-off-by: Julia Lawall Julia.Lawall@lip6.fr Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/crypto/amcc/crypto4xx_trng.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/crypto/amcc/crypto4xx_trng.c b/drivers/crypto/amcc/crypto4xx_trng.c index 677ca17fd223..368c5599515e 100644 --- a/drivers/crypto/amcc/crypto4xx_trng.c +++ b/drivers/crypto/amcc/crypto4xx_trng.c @@ -80,8 +80,10 @@ void ppc4xx_trng_probe(struct crypto4xx_core_device *core_dev)
/* Find the TRNG device node and map it */ trng = of_find_matching_node(NULL, ppc4xx_trng_match); - if (!trng || !of_device_is_available(trng)) + if (!trng || !of_device_is_available(trng)) { + of_node_put(trng); return; + }
dev->trng_base = of_iomap(trng, 0); of_node_put(trng);
From: Paul Kocialkowski paul.kocialkowski@bootlin.com
[ Upstream commit 68ef236274793066b9ba3154b16c0acc1c891e5c ]
According to the chipidea driver bindings, the USB PHY is specified via the "phys" phandle node. However, this only takes effect for USB PHYs that use the common PHY framework. For legacy USB PHYs, a simple lookup based on the USB PHY type is done instead.
This does not play out well when more than one USB PHY is registered, since the first registered PHY matching the type will always be returned regardless of what the driver was bound to.
Fix this by looking up the PHY based on the "phys" phandle node. Although generic PHYs are rather matched by their "phys-name" and not the "phys" phandle directly, there is no helper for similar lookup on legacy PHYs and it's probably not worth the effort to add it.
When no legacy USB PHY is found by phandle, fallback to grabbing any registered USB2 PHY. This ensures backward compatibility if some users were actually relying on this mechanism.
Signed-off-by: Paul Kocialkowski paul.kocialkowski@bootlin.com Signed-off-by: Peter Chen peter.chen@nxp.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/usb/chipidea/core.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-)
diff --git a/drivers/usb/chipidea/core.c b/drivers/usb/chipidea/core.c index 64c6af2c8559..e96e3a5808b3 100644 --- a/drivers/usb/chipidea/core.c +++ b/drivers/usb/chipidea/core.c @@ -901,8 +901,15 @@ static int ci_hdrc_probe(struct platform_device *pdev) } else if (ci->platdata->usb_phy) { ci->usb_phy = ci->platdata->usb_phy; } else { + ci->usb_phy = devm_usb_get_phy_by_phandle(dev->parent, "phys", + 0); ci->phy = devm_phy_get(dev->parent, "usb-phy"); - ci->usb_phy = devm_usb_get_phy(dev->parent, USB_PHY_TYPE_USB2); + + /* Fallback to grabbing any registered USB2 PHY */ + if (IS_ERR(ci->usb_phy) && + PTR_ERR(ci->usb_phy) != -EPROBE_DEFER) + ci->usb_phy = devm_usb_get_phy(dev->parent, + USB_PHY_TYPE_USB2);
/* if both generic PHY and USB PHY layers aren't enabled */ if (PTR_ERR(ci->phy) == -ENOSYS &&
From: Benjamin Block bblock@linux.ibm.com
[ Upstream commit 1749ef00f7312679f76d5e9104c5d1e22a829038 ]
We had a test-report where, under memory pressure, adding LUNs to the systems would fail (the tests add LUNs strictly in sequence):
[ 5525.853432] scsi 0:0:1:1088045124: Direct-Access IBM 2107900 .148 PQ: 0 ANSI: 5 [ 5525.853826] scsi 0:0:1:1088045124: alua: supports implicit TPGS [ 5525.853830] scsi 0:0:1:1088045124: alua: device naa.6005076303ffd32700000000000044da port group 0 rel port 43 [ 5525.853931] sd 0:0:1:1088045124: Attached scsi generic sg10 type 0 [ 5525.854075] sd 0:0:1:1088045124: [sdk] Disabling DIF Type 1 protection [ 5525.855495] sd 0:0:1:1088045124: [sdk] 2097152 512-byte logical blocks: (1.07 GB/1.00 GiB) [ 5525.855606] sd 0:0:1:1088045124: [sdk] Write Protect is off [ 5525.855609] sd 0:0:1:1088045124: [sdk] Mode Sense: ed 00 00 08 [ 5525.855795] sd 0:0:1:1088045124: [sdk] Write cache: enabled, read cache: enabled, doesn't support DPO or FUA [ 5525.857838] sdk: sdk1 [ 5525.859468] sd 0:0:1:1088045124: [sdk] Attached SCSI disk [ 5525.865073] sd 0:0:1:1088045124: alua: transition timeout set to 60 seconds [ 5525.865078] sd 0:0:1:1088045124: alua: port group 00 state A preferred supports tolusnA [ 5526.015070] sd 0:0:1:1088045124: alua: port group 00 state A preferred supports tolusnA [ 5526.015213] sd 0:0:1:1088045124: alua: port group 00 state A preferred supports tolusnA [ 5526.587439] scsi_alloc_sdev: Allocation failure during SCSI scanning, some SCSI devices might not be configured [ 5526.588562] scsi_alloc_sdev: Allocation failure during SCSI scanning, some SCSI devices might not be configured
Looking at the code of scsi_alloc_sdev(), and all the calling contexts, there seems to be no reason to use GFP_ATMOIC here. All the different call-contexts use a mutex at some point, and nothing in between that requires no sleeping, as far as I could see. Additionally, the code that later allocates the block queue for the device (scsi_mq_alloc_queue()) already uses GFP_KERNEL.
There are similar allocations in two other functions: scsi_probe_and_add_lun(), and scsi_add_lun(),; that can also be done with GFP_KERNEL.
Here is the contexts for the three functions so far:
scsi_alloc_sdev() scsi_probe_and_add_lun() scsi_sequential_lun_scan() __scsi_scan_target() scsi_scan_target() mutex_lock() scsi_scan_channel() scsi_scan_host_selected() mutex_lock() scsi_report_lun_scan() __scsi_scan_target() ... __scsi_add_device() mutex_lock() __scsi_scan_target() ... scsi_report_lun_scan() ... scsi_get_host_dev() mutex_lock()
scsi_probe_and_add_lun() ...
scsi_add_lun() scsi_probe_and_add_lun() ...
So replace all these, and give them a bit of a better chance to succeed, with more chances of reclaim.
Signed-off-by: Benjamin Block bblock@linux.ibm.com Reviewed-by: Bart Van Assche bvanassche@acm.org Signed-off-by: Martin K. Petersen martin.petersen@oracle.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/scsi/scsi_scan.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/scsi/scsi_scan.c b/drivers/scsi/scsi_scan.c index 27a6d3c6cb7c..67f6f134abc4 100644 --- a/drivers/scsi/scsi_scan.c +++ b/drivers/scsi/scsi_scan.c @@ -219,7 +219,7 @@ static struct scsi_device *scsi_alloc_sdev(struct scsi_target *starget, struct Scsi_Host *shost = dev_to_shost(starget->dev.parent);
sdev = kzalloc(sizeof(*sdev) + shost->transportt->device_size, - GFP_ATOMIC); + GFP_KERNEL); if (!sdev) goto out;
@@ -796,7 +796,7 @@ static int scsi_add_lun(struct scsi_device *sdev, unsigned char *inq_result, */ sdev->inquiry = kmemdup(inq_result, max_t(size_t, sdev->inquiry_len, 36), - GFP_ATOMIC); + GFP_KERNEL); if (sdev->inquiry == NULL) return SCSI_SCAN_NO_RESPONSE;
@@ -1095,7 +1095,7 @@ static int scsi_probe_and_add_lun(struct scsi_target *starget, if (!sdev) goto out;
- result = kmalloc(result_len, GFP_ATOMIC | + result = kmalloc(result_len, GFP_KERNEL | ((shost->unchecked_isa_dma) ? __GFP_DMA : 0)); if (!result) goto out_free_sdev;
From: Sai Prakash Ranjan saiprakash.ranjan@codeaurora.org
[ Upstream commit 5666dfd1d8a45a167f0d8b4ef47ea7f780b1f24a ]
SDM845 has ETMv4.2 and can use the existing etm4x driver. But the current etm driver checks only for ETMv4.0 and errors out for other etm4x versions. This patch adds this missing support to enable SoC's with ETMv4x to use same driver by checking only the ETM architecture major version number.
Without this change, we get below error during etm probe:
/ # dmesg | grep etm [ 6.660093] coresight-etm4x: probe of 7040000.etm failed with error -22 [ 6.666902] coresight-etm4x: probe of 7140000.etm failed with error -22 [ 6.673708] coresight-etm4x: probe of 7240000.etm failed with error -22 [ 6.680511] coresight-etm4x: probe of 7340000.etm failed with error -22 [ 6.687313] coresight-etm4x: probe of 7440000.etm failed with error -22 [ 6.694113] coresight-etm4x: probe of 7540000.etm failed with error -22 [ 6.700914] coresight-etm4x: probe of 7640000.etm failed with error -22 [ 6.707717] coresight-etm4x: probe of 7740000.etm failed with error -22
With this change, etm probe is successful:
/ # dmesg | grep etm [ 6.659198] coresight-etm4x 7040000.etm: CPU0: ETM v4.2 initialized [ 6.665848] coresight-etm4x 7140000.etm: CPU1: ETM v4.2 initialized [ 6.672493] coresight-etm4x 7240000.etm: CPU2: ETM v4.2 initialized [ 6.679129] coresight-etm4x 7340000.etm: CPU3: ETM v4.2 initialized [ 6.685770] coresight-etm4x 7440000.etm: CPU4: ETM v4.2 initialized [ 6.692403] coresight-etm4x 7540000.etm: CPU5: ETM v4.2 initialized [ 6.699024] coresight-etm4x 7640000.etm: CPU6: ETM v4.2 initialized [ 6.705646] coresight-etm4x 7740000.etm: CPU7: ETM v4.2 initialized
Signed-off-by: Sai Prakash Ranjan saiprakash.ranjan@codeaurora.org Reviewed-by: Suzuki K Poulose suzuki.poulose@arm.com Signed-off-by: Mathieu Poirier mathieu.poirier@linaro.org Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/hwtracing/coresight/coresight-etm4x.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/drivers/hwtracing/coresight/coresight-etm4x.c b/drivers/hwtracing/coresight/coresight-etm4x.c index 4db8d6a4d0cb..da27f8edba50 100644 --- a/drivers/hwtracing/coresight/coresight-etm4x.c +++ b/drivers/hwtracing/coresight/coresight-etm4x.c @@ -61,7 +61,8 @@ static void etm4_os_unlock(struct etmv4_drvdata *drvdata)
static bool etm4_arch_supported(u8 arch) { - switch (arch) { + /* Mask out the minor version number */ + switch (arch & 0xf0) { case ETM_ARCH_V4: break; default:
From: Sebastian Andrzej Siewior bigeasy@linutronix.de
[ Upstream commit 74ffe79ae538283bbf7c155e62339f1e5c87b55a ]
Mostly unwind is done with irqs enabled however SLUB may call it with irqs disabled while creating a new SLUB cache.
I had system freeze while loading a module which called kmem_cache_create() on init. That means SLUB's __slab_alloc() disabled interrupts and then
->new_slab_objects() ->new_slab() ->setup_object() ->setup_object_debug() ->init_tracking() ->set_track() ->save_stack_trace() ->save_stack_trace_tsk() ->walk_stackframe() ->unwind_frame() ->unwind_find_idx() =>spin_lock_irqsave(&unwind_lock);
Signed-off-by: Sebastian Andrzej Siewior bigeasy@linutronix.de Signed-off-by: Russell King rmk+kernel@armlinux.org.uk Signed-off-by: Sasha Levin sashal@kernel.org --- arch/arm/kernel/unwind.c | 14 +++++++------- 1 file changed, 7 insertions(+), 7 deletions(-)
diff --git a/arch/arm/kernel/unwind.c b/arch/arm/kernel/unwind.c index 0bee233fef9a..314cfb232a63 100644 --- a/arch/arm/kernel/unwind.c +++ b/arch/arm/kernel/unwind.c @@ -93,7 +93,7 @@ extern const struct unwind_idx __start_unwind_idx[]; static const struct unwind_idx *__origin_unwind_idx; extern const struct unwind_idx __stop_unwind_idx[];
-static DEFINE_SPINLOCK(unwind_lock); +static DEFINE_RAW_SPINLOCK(unwind_lock); static LIST_HEAD(unwind_tables);
/* Convert a prel31 symbol to an absolute address */ @@ -201,7 +201,7 @@ static const struct unwind_idx *unwind_find_idx(unsigned long addr) /* module unwind tables */ struct unwind_table *table;
- spin_lock_irqsave(&unwind_lock, flags); + raw_spin_lock_irqsave(&unwind_lock, flags); list_for_each_entry(table, &unwind_tables, list) { if (addr >= table->begin_addr && addr < table->end_addr) { @@ -213,7 +213,7 @@ static const struct unwind_idx *unwind_find_idx(unsigned long addr) break; } } - spin_unlock_irqrestore(&unwind_lock, flags); + raw_spin_unlock_irqrestore(&unwind_lock, flags); }
pr_debug("%s: idx = %p\n", __func__, idx); @@ -529,9 +529,9 @@ struct unwind_table *unwind_table_add(unsigned long start, unsigned long size, tab->begin_addr = text_addr; tab->end_addr = text_addr + text_size;
- spin_lock_irqsave(&unwind_lock, flags); + raw_spin_lock_irqsave(&unwind_lock, flags); list_add_tail(&tab->list, &unwind_tables); - spin_unlock_irqrestore(&unwind_lock, flags); + raw_spin_unlock_irqrestore(&unwind_lock, flags);
return tab; } @@ -543,9 +543,9 @@ void unwind_table_del(struct unwind_table *tab) if (!tab) return;
- spin_lock_irqsave(&unwind_lock, flags); + raw_spin_lock_irqsave(&unwind_lock, flags); list_del(&tab->list); - spin_unlock_irqrestore(&unwind_lock, flags); + raw_spin_unlock_irqrestore(&unwind_lock, flags);
kfree(tab); }
From: Nicolas Boichat drinkcat@chromium.org
[ Upstream commit 032ebd8548c9d05e8d2bdc7a7ec2fe29454b0ad0 ]
L1 tables are allocated with __get_dma_pages, and therefore already ignored by kmemleak.
Without this, the kernel would print this error message on boot, when the first L1 table is allocated:
[ 2.810533] kmemleak: Trying to color unknown object at 0xffffffd652388000 as Black [ 2.818190] CPU: 5 PID: 39 Comm: kworker/5:0 Tainted: G S 4.19.16 #8 [ 2.831227] Workqueue: events deferred_probe_work_func [ 2.836353] Call trace: ... [ 2.852532] paint_ptr+0xa0/0xa8 [ 2.855750] kmemleak_ignore+0x38/0x6c [ 2.859490] __arm_v7s_alloc_table+0x168/0x1f4 [ 2.863922] arm_v7s_alloc_pgtable+0x114/0x17c [ 2.868354] alloc_io_pgtable_ops+0x3c/0x78 ...
Fixes: e5fc9753b1a8314 ("iommu/io-pgtable: Add ARMv7 short descriptor support") Signed-off-by: Nicolas Boichat drinkcat@chromium.org Acked-by: Will Deacon will.deacon@arm.com Signed-off-by: Joerg Roedel jroedel@suse.de Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/iommu/io-pgtable-arm-v7s.c | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-)
diff --git a/drivers/iommu/io-pgtable-arm-v7s.c b/drivers/iommu/io-pgtable-arm-v7s.c index d68a552cfe8d..3085b47fac1d 100644 --- a/drivers/iommu/io-pgtable-arm-v7s.c +++ b/drivers/iommu/io-pgtable-arm-v7s.c @@ -207,7 +207,8 @@ static void *__arm_v7s_alloc_table(int lvl, gfp_t gfp, if (dma != virt_to_phys(table)) goto out_unmap; } - kmemleak_ignore(table); + if (lvl == 2) + kmemleak_ignore(table); return table;
out_unmap:
From: Aaro Koskinen aaro.koskinen@iki.fi
[ Upstream commit a6327b5e57fdc679c842588c3be046c0b39cc127 ]
When running OMAP1 kernel on QEMU, MMC access is annoyingly noisy:
MMC: CTO of 0xff and 0xfe cannot be used! MMC: CTO of 0xff and 0xfe cannot be used! MMC: CTO of 0xff and 0xfe cannot be used! [ad inf.]
Emulator warnings appear to be valid. The TI document SPRU680 [1] ("OMAP5910 Dual-Core Processor MultiMedia Card/Secure Data Memory Card (MMC/SD) Reference Guide") page 36 states that the maximum timeout is 253 cycles and "0xff and 0xfe cannot be used".
Fix by using 0xfd as the maximum timeout.
Tested using QEMU 2.5 (Siemens SX1 machine, OMAP310), and also checked on real hardware using Palm TE (OMAP310), Nokia 770 (OMAP1710) and Nokia N810 (OMAP2420) that MMC works as before.
[1] http://www.ti.com/lit/ug/spru680/spru680.pdf
Fixes: 730c9b7e6630f ("[MMC] Add OMAP MMC host driver") Signed-off-by: Aaro Koskinen aaro.koskinen@iki.fi Signed-off-by: Ulf Hansson ulf.hansson@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/mmc/host/omap.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/mmc/host/omap.c b/drivers/mmc/host/omap.c index a4bf14e21b5e..21dfce21aa63 100644 --- a/drivers/mmc/host/omap.c +++ b/drivers/mmc/host/omap.c @@ -920,7 +920,7 @@ static inline void set_cmd_timeout(struct mmc_omap_host *host, struct mmc_reques reg &= ~(1 << 5); OMAP_MMC_WRITE(host, SDIO, reg); /* Set maximum timeout */ - OMAP_MMC_WRITE(host, CTO, 0xff); + OMAP_MMC_WRITE(host, CTO, 0xfd); }
static inline void set_data_timeout(struct mmc_omap_host *host, struct mmc_request *req)
From: Florian Fainelli f.fainelli@gmail.com
[ Upstream commit 135e7245479addc6b1f5d031e3d7e2ddb3d2b109 ]
Provide precision hints to snprintf() since we know the destination buffer size of the RX/TX ring names are IFNAMSIZ + 5 - 1. This fixes the following warnings:
drivers/net/ethernet/intel/e1000e/netdev.c: In function 'e1000_request_msix': drivers/net/ethernet/intel/e1000e/netdev.c:2109:13: warning: 'snprintf' output may be truncated before the last format character [-Wformat-truncation=] "%s-rx-0", netdev->name); ^ drivers/net/ethernet/intel/e1000e/netdev.c:2107:3: note: 'snprintf' output between 6 and 21 bytes into a destination of size 20 snprintf(adapter->rx_ring->name, ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ sizeof(adapter->rx_ring->name) - 1, ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ "%s-rx-0", netdev->name); ~~~~~~~~~~~~~~~~~~~~~~~~ drivers/net/ethernet/intel/e1000e/netdev.c:2125:13: warning: 'snprintf' output may be truncated before the last format character [-Wformat-truncation=] "%s-tx-0", netdev->name); ^ drivers/net/ethernet/intel/e1000e/netdev.c:2123:3: note: 'snprintf' output between 6 and 21 bytes into a destination of size 20 snprintf(adapter->tx_ring->name, ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ sizeof(adapter->tx_ring->name) - 1, ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ "%s-tx-0", netdev->name); ~~~~~~~~~~~~~~~~~~~~~~~~
Signed-off-by: Florian Fainelli f.fainelli@gmail.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/intel/e1000e/netdev.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/net/ethernet/intel/e1000e/netdev.c b/drivers/net/ethernet/intel/e1000e/netdev.c index 6855b3380a83..f56f8b6e2378 100644 --- a/drivers/net/ethernet/intel/e1000e/netdev.c +++ b/drivers/net/ethernet/intel/e1000e/netdev.c @@ -2121,7 +2121,7 @@ static int e1000_request_msix(struct e1000_adapter *adapter) if (strlen(netdev->name) < (IFNAMSIZ - 5)) snprintf(adapter->rx_ring->name, sizeof(adapter->rx_ring->name) - 1, - "%s-rx-0", netdev->name); + "%.14s-rx-0", netdev->name); else memcpy(adapter->rx_ring->name, netdev->name, IFNAMSIZ); err = request_irq(adapter->msix_entries[vector].vector, @@ -2137,7 +2137,7 @@ static int e1000_request_msix(struct e1000_adapter *adapter) if (strlen(netdev->name) < (IFNAMSIZ - 5)) snprintf(adapter->tx_ring->name, sizeof(adapter->tx_ring->name) - 1, - "%s-tx-0", netdev->name); + "%.14s-tx-0", netdev->name); else memcpy(adapter->tx_ring->name, netdev->name, IFNAMSIZ); err = request_irq(adapter->msix_entries[vector].vector,
From: Florian Fainelli f.fainelli@gmail.com
[ Upstream commit ab2c4e2581ad32c28627235ff0ae8c5a5ea6899f ]
Give precision identifiers to the two snprintf() formatting the priority and TC strings to avoid producing these two warnings:
drivers/net/ethernet/mellanox/mlxsw/spectrum.c: In function 'mlxsw_sp_port_get_prio_strings': drivers/net/ethernet/mellanox/mlxsw/spectrum.c:2132:37: warning: '%d' directive output may be truncated writing between 1 and 3 bytes into a region of size between 0 and 31 [-Wformat-truncation=] snprintf(*p, ETH_GSTRING_LEN, "%s_%d", ^~ drivers/net/ethernet/mellanox/mlxsw/spectrum.c:2132:3: note: 'snprintf' output between 3 and 36 bytes into a destination of size 32 snprintf(*p, ETH_GSTRING_LEN, "%s_%d", ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ mlxsw_sp_port_hw_prio_stats[i].str, prio); ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ drivers/net/ethernet/mellanox/mlxsw/spectrum.c: In function 'mlxsw_sp_port_get_tc_strings': drivers/net/ethernet/mellanox/mlxsw/spectrum.c:2143:37: warning: '%d' directive output may be truncated writing between 1 and 11 bytes into a region of size between 0 and 31 [-Wformat-truncation=] snprintf(*p, ETH_GSTRING_LEN, "%s_%d", ^~ drivers/net/ethernet/mellanox/mlxsw/spectrum.c:2143:3: note: 'snprintf' output between 3 and 44 bytes into a destination of size 32 snprintf(*p, ETH_GSTRING_LEN, "%s_%d", ^~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ mlxsw_sp_port_hw_tc_stats[i].str, tc); ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~
Signed-off-by: Florian Fainelli f.fainelli@gmail.com Reviewed-by: Ido Schimmel idosch@mellanox.com Signed-off-by: David S. Miller davem@davemloft.net Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/mellanox/mlxsw/spectrum.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/net/ethernet/mellanox/mlxsw/spectrum.c b/drivers/net/ethernet/mellanox/mlxsw/spectrum.c index 22a5916e477e..cc847e0cac2d 100644 --- a/drivers/net/ethernet/mellanox/mlxsw/spectrum.c +++ b/drivers/net/ethernet/mellanox/mlxsw/spectrum.c @@ -1565,7 +1565,7 @@ static void mlxsw_sp_port_get_prio_strings(u8 **p, int prio) int i;
for (i = 0; i < MLXSW_SP_PORT_HW_PRIO_STATS_LEN; i++) { - snprintf(*p, ETH_GSTRING_LEN, "%s_%d", + snprintf(*p, ETH_GSTRING_LEN, "%.29s_%.1d", mlxsw_sp_port_hw_prio_stats[i].str, prio); *p += ETH_GSTRING_LEN; } @@ -1576,7 +1576,7 @@ static void mlxsw_sp_port_get_tc_strings(u8 **p, int tc) int i;
for (i = 0; i < MLXSW_SP_PORT_HW_TC_STATS_LEN; i++) { - snprintf(*p, ETH_GSTRING_LEN, "%s_%d", + snprintf(*p, ETH_GSTRING_LEN, "%.29s_%.1d", mlxsw_sp_port_hw_tc_stats[i].str, tc); *p += ETH_GSTRING_LEN; }
From: Håkon Bugge haakon.bugge@oracle.com
[ Upstream commit 2612d723aadcf8281f9bf8305657129bd9f3cd57 ]
Using CX-3 virtual functions, either from a bare-metal machine or pass-through from a VM, MAD packets are proxied through the PF driver.
Since the VF drivers have separate name spaces for MAD Transaction Ids (TIDs), the PF driver has to re-map the TIDs and keep the book keeping in a cache.
Following the RDMA Connection Manager (CM) protocol, it is clear when an entry has to evicted form the cache. But life is not perfect, remote peers may die or be rebooted. Hence, it's a timeout to wipe out a cache entry, when the PF driver assumes the remote peer has gone.
During workloads where a high number of QPs are destroyed concurrently, excessive amount of CM DREQ retries has been observed
The problem can be demonstrated in a bare-metal environment, where two nodes have instantiated 8 VFs each. This using dual ported HCAs, so we have 16 vPorts per physical server.
64 processes are associated with each vPort and creates and destroys one QP for each of the remote 64 processes. That is, 1024 QPs per vPort, all in all 16K QPs. The QPs are created/destroyed using the CM.
When tearing down these 16K QPs, excessive CM DREQ retries (and duplicates) are observed. With some cat/paste/awk wizardry on the infiniband_cm sysfs, we observe as sum of the 16 vPorts on one of the nodes:
cm_rx_duplicates: dreq 2102 cm_rx_msgs: drep 1989 dreq 6195 rep 3968 req 4224 rtu 4224 cm_tx_msgs: drep 4093 dreq 27568 rep 4224 req 3968 rtu 3968 cm_tx_retries: dreq 23469
Note that the active/passive side is equally distributed between the two nodes.
Enabling pr_debug in cm.c gives tons of:
[171778.814239] <mlx4_ib> mlx4_ib_multiplex_cm_handler: id{slave: 1,sl_cm_id: 0xd393089f} is NULL!
By increasing the CM_CLEANUP_CACHE_TIMEOUT from 5 to 30 seconds, the tear-down phase of the application is reduced from approximately 90 to 50 seconds. Retries/duplicates are also significantly reduced:
cm_rx_duplicates: dreq 2460 [] cm_tx_retries: dreq 3010 req 47
Increasing the timeout further didn't help, as these duplicates and retries stems from a too short CMA timeout, which was 20 (~4 seconds) on the systems. By increasing the CMA timeout to 22 (~17 seconds), the numbers fell down to about 10 for both of them.
Adjustment of the CMA timeout is not part of this commit.
Signed-off-by: Håkon Bugge haakon.bugge@oracle.com Acked-by: Jack Morgenstein jackm@dev.mellanox.co.il Signed-off-by: Jason Gunthorpe jgg@mellanox.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/infiniband/hw/mlx4/cm.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/infiniband/hw/mlx4/cm.c b/drivers/infiniband/hw/mlx4/cm.c index 39a488889fc7..5dc920fe1326 100644 --- a/drivers/infiniband/hw/mlx4/cm.c +++ b/drivers/infiniband/hw/mlx4/cm.c @@ -39,7 +39,7 @@
#include "mlx4_ib.h"
-#define CM_CLEANUP_CACHE_TIMEOUT (5 * HZ) +#define CM_CLEANUP_CACHE_TIMEOUT (30 * HZ)
struct id_map_entry { struct rb_node node;
From: Takashi Iwai tiwai@suse.de
[ Upstream commit 8d1667200850f8753c0265fa4bd25c9a6e5f94ce ]
The apq8016 driver leaves the of-node refcount at aborting from the loop of for_each_child_of_node() in the error path. Not only the iterator node of for_each_child_of_node(), the children nodes referred from it for codec and cpu have to be properly unreferenced.
Fixes: bdb052e81f62 ("ASoC: qcom: add apq8016 sound card support") Cc: Patrick Lai plai@codeaurora.org Cc: Banajit Goswami bgoswami@codeaurora.org Signed-off-by: Takashi Iwai tiwai@suse.de Signed-off-by: Mark Brown broonie@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- sound/soc/qcom/apq8016_sbc.c | 21 ++++++++++++++++----- 1 file changed, 16 insertions(+), 5 deletions(-)
diff --git a/sound/soc/qcom/apq8016_sbc.c b/sound/soc/qcom/apq8016_sbc.c index 07f91e918b23..754742018515 100644 --- a/sound/soc/qcom/apq8016_sbc.c +++ b/sound/soc/qcom/apq8016_sbc.c @@ -114,13 +114,15 @@ static struct apq8016_sbc_data *apq8016_sbc_parse_of(struct snd_soc_card *card)
if (!cpu || !codec) { dev_err(dev, "Can't find cpu/codec DT node\n"); - return ERR_PTR(-EINVAL); + ret = -EINVAL; + goto error; }
link->cpu_of_node = of_parse_phandle(cpu, "sound-dai", 0); if (!link->cpu_of_node) { dev_err(card->dev, "error getting cpu phandle\n"); - return ERR_PTR(-EINVAL); + ret = -EINVAL; + goto error; }
link->codec_of_node = of_parse_phandle(codec, "sound-dai", 0); @@ -132,28 +134,37 @@ static struct apq8016_sbc_data *apq8016_sbc_parse_of(struct snd_soc_card *card) ret = snd_soc_of_get_dai_name(cpu, &link->cpu_dai_name); if (ret) { dev_err(card->dev, "error getting cpu dai name\n"); - return ERR_PTR(ret); + goto error; }
ret = snd_soc_of_get_dai_name(codec, &link->codec_dai_name); if (ret) { dev_err(card->dev, "error getting codec dai name\n"); - return ERR_PTR(ret); + goto error; }
link->platform_of_node = link->cpu_of_node; ret = of_property_read_string(np, "link-name", &link->name); if (ret) { dev_err(card->dev, "error getting codec dai_link name\n"); - return ERR_PTR(ret); + goto error; }
link->stream_name = link->name; link->init = apq8016_sbc_dai_init; link++; + + of_node_put(cpu); + of_node_put(codec); }
return data; + + error: + of_node_put(np); + of_node_put(cpu); + of_node_put(codec); + return ERR_PTR(ret); }
static const struct snd_soc_dapm_widget apq8016_sbc_dapm_widgets[] = {
From: Jason Yan yanaijie@huawei.com
[ Upstream commit bcf3b67d16a4c8ffae0aa79de5853435e683945c ]
when create DMA pool for cmd frames failed, we should return -ENOMEM, instead of 0. In some case in:
megasas_init_adapter_fusion()
-->megasas_alloc_cmds() -->megasas_create_frame_pool create DMA pool failed, --> megasas_free_cmds() [1]
-->megasas_alloc_cmds_fusion() failed, then goto fail_alloc_cmds. -->megasas_free_cmds() [2]
we will call megasas_free_cmds twice, [1] will kfree cmd_list, [2] will use cmd_list.it will cause a problem:
Unable to handle kernel NULL pointer dereference at virtual address 00000000 pgd = ffffffc000f70000 [00000000] *pgd=0000001fbf893003, *pud=0000001fbf893003, *pmd=0000001fbf894003, *pte=006000006d000707 Internal error: Oops: 96000005 [#1] SMP Modules linked in: CPU: 18 PID: 1 Comm: swapper/0 Not tainted task: ffffffdfb9290000 ti: ffffffdfb923c000 task.ti: ffffffdfb923c000 PC is at megasas_free_cmds+0x30/0x70 LR is at megasas_free_cmds+0x24/0x70 ... Call trace: [<ffffffc0005b779c>] megasas_free_cmds+0x30/0x70 [<ffffffc0005bca74>] megasas_init_adapter_fusion+0x2f4/0x4d8 [<ffffffc0005b926c>] megasas_init_fw+0x2dc/0x760 [<ffffffc0005b9ab0>] megasas_probe_one+0x3c0/0xcd8 [<ffffffc0004a5abc>] local_pci_probe+0x4c/0xb4 [<ffffffc0004a5c40>] pci_device_probe+0x11c/0x14c [<ffffffc00053a5e4>] driver_probe_device+0x1ec/0x430 [<ffffffc00053a92c>] __driver_attach+0xa8/0xb0 [<ffffffc000538178>] bus_for_each_dev+0x74/0xc8 [<ffffffc000539e88>] driver_attach+0x28/0x34 [<ffffffc000539a18>] bus_add_driver+0x16c/0x248 [<ffffffc00053b234>] driver_register+0x6c/0x138 [<ffffffc0004a5350>] __pci_register_driver+0x5c/0x6c [<ffffffc000ce3868>] megasas_init+0xc0/0x1a8 [<ffffffc000082a58>] do_one_initcall+0xe8/0x1ec [<ffffffc000ca7be8>] kernel_init_freeable+0x1c8/0x284 [<ffffffc0008d90b8>] kernel_init+0x1c/0xe4
Signed-off-by: Jason Yan yanaijie@huawei.com Acked-by: Sumit Saxena sumit.saxena@broadcom.com Signed-off-by: Martin K. Petersen martin.petersen@oracle.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/scsi/megaraid/megaraid_sas_base.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/scsi/megaraid/megaraid_sas_base.c b/drivers/scsi/megaraid/megaraid_sas_base.c index 5de024a50e15..5b1c37e3913c 100644 --- a/drivers/scsi/megaraid/megaraid_sas_base.c +++ b/drivers/scsi/megaraid/megaraid_sas_base.c @@ -3956,6 +3956,7 @@ int megasas_alloc_cmds(struct megasas_instance *instance) if (megasas_create_frame_pool(instance)) { dev_printk(KERN_DEBUG, &instance->pdev->dev, "Error creating frame DMA pool\n"); megasas_free_cmds(instance); + return -ENOMEM; }
return 0;
From: Thomas Richter tmricht@linux.ibm.com
[ Upstream commit 03d309711d687460d1345de8a0363f45b1c8cd11 ]
Commit 489338a717a0 ("perf tests evsel-tp-sched: Fix bitwise operator") causes test case 14 "Parse sched tracepoints fields" to fail on s390.
This test succeeds on x86.
In fact this test now fails on all architectures with type char treated as type unsigned char.
The root cause is the signed-ness of character arrays in the tracepoints sched_switch for structure members prev_comm and next_comm.
On s390 the output of:
[root@m35lp76 perf]# cat /sys/kernel/debug/tracing/events/sched/sched_switch/format name: sched_switch ID: 287 format: field:unsigned short common_type; offset:0; size:2; signed:0; ... field:char prev_comm[16]; offset:8; size:16; signed:0; ... field:char next_comm[16]; offset:40; size:16; signed:0;
reveals the character arrays prev_comm and next_comm are per default unsigned char and have values in the range of 0..255.
On x86 both fields are signed as this output shows: [root@f29]# cat /sys/kernel/debug/tracing/events/sched/sched_switch/format name: sched_switch ID: 287 format: field:unsigned short common_type; offset:0; size:2; signed:0; ... field:char prev_comm[16]; offset:8; size:16; signed:1; ... field:char next_comm[16]; offset:40; size:16; signed:1;
and the character arrays prev_comm and next_comm are per default signed char and have values in the range of -1..127. The implementation of type char is architecture specific.
Since the character arrays in both tracepoints sched_switch and sched_wakeup should contain ascii characters, simply omit the check for signedness in the test case.
Output before:
[root@m35lp76 perf]# ./perf test -F 14 14: Parse sched tracepoints fields : --- start --- sched:sched_switch: "prev_comm" signedness(0) is wrong, should be 1 sched:sched_switch: "next_comm" signedness(0) is wrong, should be 1 sched:sched_wakeup: "comm" signedness(0) is wrong, should be 1 ---- end ---- 14: Parse sched tracepoints fields : FAILED! [root@m35lp76 perf]#
Output after:
[root@m35lp76 perf]# ./perf test -Fv 14 14: Parse sched tracepoints fields : --- start --- ---- end ---- Parse sched tracepoints fields: Ok [root@m35lp76 perf]#
Fixes: 489338a717a0 ("perf tests evsel-tp-sched: Fix bitwise operator")
Signed-off-by: Thomas Richter tmricht@linux.ibm.com Cc: Heiko Carstens heiko.carstens@de.ibm.com Cc: Hendrik Brueckner brueckner@linux.vnet.ibm.com Cc: Martin Schwidefsky schwidefsky@de.ibm.com Link: http://lkml.kernel.org/r/20190219153639.31267-1-tmricht@linux.ibm.com Signed-off-by: Arnaldo Carvalho de Melo acme@redhat.com Signed-off-by: Sasha Levin sashal@kernel.org --- tools/perf/tests/evsel-tp-sched.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/tools/perf/tests/evsel-tp-sched.c b/tools/perf/tests/evsel-tp-sched.c index 66b53f10eb18..ea772d41e472 100644 --- a/tools/perf/tests/evsel-tp-sched.c +++ b/tools/perf/tests/evsel-tp-sched.c @@ -42,7 +42,7 @@ int test__perf_evsel__tp_sched_test(int subtest __maybe_unused) return -1; }
- if (perf_evsel__test_field(evsel, "prev_comm", 16, true)) + if (perf_evsel__test_field(evsel, "prev_comm", 16, false)) ret = -1;
if (perf_evsel__test_field(evsel, "prev_pid", 4, true)) @@ -54,7 +54,7 @@ int test__perf_evsel__tp_sched_test(int subtest __maybe_unused) if (perf_evsel__test_field(evsel, "prev_state", sizeof(long), true)) ret = -1;
- if (perf_evsel__test_field(evsel, "next_comm", 16, true)) + if (perf_evsel__test_field(evsel, "next_comm", 16, false)) ret = -1;
if (perf_evsel__test_field(evsel, "next_pid", 4, true)) @@ -72,7 +72,7 @@ int test__perf_evsel__tp_sched_test(int subtest __maybe_unused) return -1; }
- if (perf_evsel__test_field(evsel, "comm", 16, true)) + if (perf_evsel__test_field(evsel, "comm", 16, false)) ret = -1;
if (perf_evsel__test_field(evsel, "pid", 4, true))
From: Wen Yang yellowriver2010@hotmail.com
[ Upstream commit 8fa857da9744f513036df1c43ab57f338941ae7d ]
The of_find_device_by_node() takes a reference to the underlying device structure, we should release that reference.
Detected by coccinelle with the following warnings: ./sound/soc/fsl/imx-sgtl5000.c:169:1-7: ERROR: missing put_device; call of_find_device_by_node on line 105, but without a corresponding object release within this function. ./sound/soc/fsl/imx-sgtl5000.c:177:1-7: ERROR: missing put_device; call of_find_device_by_node on line 105, but without a corresponding object release within this function.
Signed-off-by: Wen Yang yellowriver2010@hotmail.com Cc: Timur Tabi timur@kernel.org Cc: Nicolin Chen nicoleotsuka@gmail.com Cc: Xiubo Li Xiubo.Lee@gmail.com Cc: Fabio Estevam festevam@gmail.com Cc: Liam Girdwood lgirdwood@gmail.com Cc: Mark Brown broonie@kernel.org Cc: Jaroslav Kysela perex@perex.cz Cc: Takashi Iwai tiwai@suse.com Cc: Shawn Guo shawnguo@kernel.org Cc: Sascha Hauer s.hauer@pengutronix.de Cc: Pengutronix Kernel Team kernel@pengutronix.de Cc: NXP Linux Team linux-imx@nxp.com Cc: alsa-devel@alsa-project.org Cc: linuxppc-dev@lists.ozlabs.org Cc: linux-arm-kernel@lists.infradead.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Mark Brown broonie@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- sound/soc/fsl/imx-sgtl5000.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/sound/soc/fsl/imx-sgtl5000.c b/sound/soc/fsl/imx-sgtl5000.c index b99e0b5e00e9..8e525f7ac08d 100644 --- a/sound/soc/fsl/imx-sgtl5000.c +++ b/sound/soc/fsl/imx-sgtl5000.c @@ -115,6 +115,7 @@ static int imx_sgtl5000_probe(struct platform_device *pdev) ret = -EPROBE_DEFER; goto fail; } + put_device(&ssi_pdev->dev); codec_dev = of_find_i2c_device_by_node(codec_np); if (!codec_dev) { dev_err(&pdev->dev, "failed to find codec platform device\n");
From: Ezequiel Garcia ezequiel@collabora.com
[ Upstream commit 43c145195c7fc3025ee7ecfc67112ac1c82af7c2 ]
Fix the assigned type of mem2mem buffer handling API. Namely, these functions:
v4l2_m2m_next_buf v4l2_m2m_last_buf v4l2_m2m_buf_remove v4l2_m2m_next_src_buf v4l2_m2m_next_dst_buf v4l2_m2m_last_src_buf v4l2_m2m_last_dst_buf v4l2_m2m_src_buf_remove v4l2_m2m_dst_buf_remove
return a struct vb2_v4l2_buffer, and not a struct vb2_buffer.
Fixing this is necessary to fix the mem2mem buffer handling API, changing the return to the correct struct vb2_v4l2_buffer instead of a void pointer.
Signed-off-by: Ezequiel Garcia ezequiel@collabora.com Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/sh_veu.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/media/platform/sh_veu.c b/drivers/media/platform/sh_veu.c index 15a562af13c7..a4f593220ef0 100644 --- a/drivers/media/platform/sh_veu.c +++ b/drivers/media/platform/sh_veu.c @@ -276,13 +276,13 @@ static void sh_veu_process(struct sh_veu_dev *veu, static void sh_veu_device_run(void *priv) { struct sh_veu_dev *veu = priv; - struct vb2_buffer *src_buf, *dst_buf; + struct vb2_v4l2_buffer *src_buf, *dst_buf;
src_buf = v4l2_m2m_next_src_buf(veu->m2m_ctx); dst_buf = v4l2_m2m_next_dst_buf(veu->m2m_ctx);
if (src_buf && dst_buf) - sh_veu_process(veu, src_buf, dst_buf); + sh_veu_process(veu, &src_buf->vb2_buf, &dst_buf->vb2_buf); }
/* ========== video ioctls ========== */
From: Ezequiel Garcia ezequiel@collabora.com
[ Upstream commit 4a88f89885c7cf65c62793f385261a6e3315178a ]
Fix the assigned type of mem2mem buffer handling API. Namely, these functions:
v4l2_m2m_next_buf v4l2_m2m_last_buf v4l2_m2m_buf_remove v4l2_m2m_next_src_buf v4l2_m2m_next_dst_buf v4l2_m2m_last_src_buf v4l2_m2m_last_dst_buf v4l2_m2m_src_buf_remove v4l2_m2m_dst_buf_remove
return a struct vb2_v4l2_buffer, and not a struct vb2_buffer.
Fixing this is necessary to fix the mem2mem buffer handling API, changing the return to the correct struct vb2_v4l2_buffer instead of a void pointer.
Signed-off-by: Ezequiel Garcia ezequiel@collabora.com Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/s5p-jpeg/jpeg-core.c | 38 ++++++++++----------- 1 file changed, 19 insertions(+), 19 deletions(-)
diff --git a/drivers/media/platform/s5p-jpeg/jpeg-core.c b/drivers/media/platform/s5p-jpeg/jpeg-core.c index 1da2c94e1dca..06e2b72d07ca 100644 --- a/drivers/media/platform/s5p-jpeg/jpeg-core.c +++ b/drivers/media/platform/s5p-jpeg/jpeg-core.c @@ -789,14 +789,14 @@ static void skip(struct s5p_jpeg_buffer *buf, long len); static void exynos4_jpeg_parse_decode_h_tbl(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); + struct vb2_v4l2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); struct s5p_jpeg_buffer jpeg_buffer; unsigned int word; int c, x, components;
jpeg_buffer.size = 2; /* Ls */ jpeg_buffer.data = - (unsigned long)vb2_plane_vaddr(vb, 0) + ctx->out_q.sos + 2; + (unsigned long)vb2_plane_vaddr(&vb->vb2_buf, 0) + ctx->out_q.sos + 2; jpeg_buffer.curr = 0;
word = 0; @@ -826,14 +826,14 @@ static void exynos4_jpeg_parse_decode_h_tbl(struct s5p_jpeg_ctx *ctx) static void exynos4_jpeg_parse_huff_tbl(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); + struct vb2_v4l2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); struct s5p_jpeg_buffer jpeg_buffer; unsigned int word; int c, i, n, j;
for (j = 0; j < ctx->out_q.dht.n; ++j) { jpeg_buffer.size = ctx->out_q.dht.len[j]; - jpeg_buffer.data = (unsigned long)vb2_plane_vaddr(vb, 0) + + jpeg_buffer.data = (unsigned long)vb2_plane_vaddr(&vb->vb2_buf, 0) + ctx->out_q.dht.marker[j]; jpeg_buffer.curr = 0;
@@ -885,13 +885,13 @@ static void exynos4_jpeg_parse_huff_tbl(struct s5p_jpeg_ctx *ctx) static void exynos4_jpeg_parse_decode_q_tbl(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); + struct vb2_v4l2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); struct s5p_jpeg_buffer jpeg_buffer; int c, x, components;
jpeg_buffer.size = ctx->out_q.sof_len; jpeg_buffer.data = - (unsigned long)vb2_plane_vaddr(vb, 0) + ctx->out_q.sof; + (unsigned long)vb2_plane_vaddr(&vb->vb2_buf, 0) + ctx->out_q.sof; jpeg_buffer.curr = 0;
skip(&jpeg_buffer, 5); /* P, Y, X */ @@ -916,14 +916,14 @@ static void exynos4_jpeg_parse_decode_q_tbl(struct s5p_jpeg_ctx *ctx) static void exynos4_jpeg_parse_q_tbl(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); + struct vb2_v4l2_buffer *vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); struct s5p_jpeg_buffer jpeg_buffer; unsigned int word; int c, i, j;
for (j = 0; j < ctx->out_q.dqt.n; ++j) { jpeg_buffer.size = ctx->out_q.dqt.len[j]; - jpeg_buffer.data = (unsigned long)vb2_plane_vaddr(vb, 0) + + jpeg_buffer.data = (unsigned long)vb2_plane_vaddr(&vb->vb2_buf, 0) + ctx->out_q.dqt.marker[j]; jpeg_buffer.curr = 0;
@@ -2027,15 +2027,15 @@ static void s5p_jpeg_device_run(void *priv) { struct s5p_jpeg_ctx *ctx = priv; struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *src_buf, *dst_buf; + struct vb2_v4l2_buffer *src_buf, *dst_buf; unsigned long src_addr, dst_addr, flags;
spin_lock_irqsave(&ctx->jpeg->slock, flags);
src_buf = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx); dst_buf = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx); - src_addr = vb2_dma_contig_plane_dma_addr(src_buf, 0); - dst_addr = vb2_dma_contig_plane_dma_addr(dst_buf, 0); + src_addr = vb2_dma_contig_plane_dma_addr(&src_buf->vb2_buf, 0); + dst_addr = vb2_dma_contig_plane_dma_addr(&dst_buf->vb2_buf, 0);
s5p_jpeg_reset(jpeg->regs); s5p_jpeg_poweron(jpeg->regs); @@ -2108,7 +2108,7 @@ static void exynos4_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; struct s5p_jpeg_fmt *fmt; - struct vb2_buffer *vb; + struct vb2_v4l2_buffer *vb; struct s5p_jpeg_addr jpeg_addr = {}; u32 pix_size, padding_bytes = 0;
@@ -2127,7 +2127,7 @@ static void exynos4_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx) vb = v4l2_m2m_next_dst_buf(ctx->fh.m2m_ctx); }
- jpeg_addr.y = vb2_dma_contig_plane_dma_addr(vb, 0); + jpeg_addr.y = vb2_dma_contig_plane_dma_addr(&vb->vb2_buf, 0);
if (fmt->colplanes == 2) { jpeg_addr.cb = jpeg_addr.y + pix_size - padding_bytes; @@ -2145,7 +2145,7 @@ static void exynos4_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx) static void exynos4_jpeg_set_jpeg_addr(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *vb; + struct vb2_v4l2_buffer *vb; unsigned int jpeg_addr = 0;
if (ctx->mode == S5P_JPEG_ENCODE) @@ -2153,7 +2153,7 @@ static void exynos4_jpeg_set_jpeg_addr(struct s5p_jpeg_ctx *ctx) else vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
- jpeg_addr = vb2_dma_contig_plane_dma_addr(vb, 0); + jpeg_addr = vb2_dma_contig_plane_dma_addr(&vb->vb2_buf, 0); if (jpeg->variant->version == SJPEG_EXYNOS5433 && ctx->mode == S5P_JPEG_DECODE) jpeg_addr += ctx->out_q.sos; @@ -2268,7 +2268,7 @@ static void exynos3250_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; struct s5p_jpeg_fmt *fmt; - struct vb2_buffer *vb; + struct vb2_v4l2_buffer *vb; struct s5p_jpeg_addr jpeg_addr = {}; u32 pix_size;
@@ -2282,7 +2282,7 @@ static void exynos3250_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx) fmt = ctx->cap_q.fmt; }
- jpeg_addr.y = vb2_dma_contig_plane_dma_addr(vb, 0); + jpeg_addr.y = vb2_dma_contig_plane_dma_addr(&vb->vb2_buf, 0);
if (fmt->colplanes == 2) { jpeg_addr.cb = jpeg_addr.y + pix_size; @@ -2300,7 +2300,7 @@ static void exynos3250_jpeg_set_img_addr(struct s5p_jpeg_ctx *ctx) static void exynos3250_jpeg_set_jpeg_addr(struct s5p_jpeg_ctx *ctx) { struct s5p_jpeg *jpeg = ctx->jpeg; - struct vb2_buffer *vb; + struct vb2_v4l2_buffer *vb; unsigned int jpeg_addr = 0;
if (ctx->mode == S5P_JPEG_ENCODE) @@ -2308,7 +2308,7 @@ static void exynos3250_jpeg_set_jpeg_addr(struct s5p_jpeg_ctx *ctx) else vb = v4l2_m2m_next_src_buf(ctx->fh.m2m_ctx);
- jpeg_addr = vb2_dma_contig_plane_dma_addr(vb, 0); + jpeg_addr = vb2_dma_contig_plane_dma_addr(&vb->vb2_buf, 0); exynos3250_jpeg_jpgadr(jpeg->regs, jpeg_addr); }
From: Ezequiel Garcia ezequiel@collabora.com
[ Upstream commit 30fa627b32230737bc3f678067e2adfecf956987 ]
Fix the assigned type of mem2mem buffer handling API. Namely, these functions:
v4l2_m2m_next_buf v4l2_m2m_last_buf v4l2_m2m_buf_remove v4l2_m2m_next_src_buf v4l2_m2m_next_dst_buf v4l2_m2m_last_src_buf v4l2_m2m_last_dst_buf v4l2_m2m_src_buf_remove v4l2_m2m_dst_buf_remove
return a struct vb2_v4l2_buffer, and not a struct vb2_buffer.
Fixing this is necessary to fix the mem2mem buffer handling API, changing the return to the correct struct vb2_v4l2_buffer instead of a void pointer.
Signed-off-by: Ezequiel Garcia ezequiel@collabora.com Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/s5p-g2d/g2d.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/media/platform/s5p-g2d/g2d.c b/drivers/media/platform/s5p-g2d/g2d.c index 62c0dec30b59..5f6ccf492111 100644 --- a/drivers/media/platform/s5p-g2d/g2d.c +++ b/drivers/media/platform/s5p-g2d/g2d.c @@ -498,7 +498,7 @@ static void device_run(void *prv) { struct g2d_ctx *ctx = prv; struct g2d_dev *dev = ctx->dev; - struct vb2_buffer *src, *dst; + struct vb2_v4l2_buffer *src, *dst; unsigned long flags; u32 cmd = 0;
@@ -513,10 +513,10 @@ static void device_run(void *prv) spin_lock_irqsave(&dev->ctrl_lock, flags);
g2d_set_src_size(dev, &ctx->in); - g2d_set_src_addr(dev, vb2_dma_contig_plane_dma_addr(src, 0)); + g2d_set_src_addr(dev, vb2_dma_contig_plane_dma_addr(&src->vb2_buf, 0));
g2d_set_dst_size(dev, &ctx->out); - g2d_set_dst_addr(dev, vb2_dma_contig_plane_dma_addr(dst, 0)); + g2d_set_dst_addr(dev, vb2_dma_contig_plane_dma_addr(&dst->vb2_buf, 0));
g2d_set_rop4(dev, ctx->rop); g2d_set_flip(dev, ctx->flip);
From: Ezequiel Garcia ezequiel@collabora.com
[ Upstream commit 8d20dcefe471763f23ad538369ec65b51993ffff ]
Fix the assigned type of mem2mem buffer handling API. Namely, these functions:
v4l2_m2m_next_buf v4l2_m2m_last_buf v4l2_m2m_buf_remove v4l2_m2m_next_src_buf v4l2_m2m_next_dst_buf v4l2_m2m_last_src_buf v4l2_m2m_last_dst_buf v4l2_m2m_src_buf_remove v4l2_m2m_dst_buf_remove
return a struct vb2_v4l2_buffer, and not a struct vb2_buffer.
Fixing this is necessary to fix the mem2mem buffer handling API, changing the return to the correct struct vb2_v4l2_buffer instead of a void pointer.
Signed-off-by: Ezequiel Garcia ezequiel@collabora.com Signed-off-by: Hans Verkuil hverkuil-cisco@xs4all.nl Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/mx2_emmaprp.c | 6 +++--- 1 file changed, 3 insertions(+), 3 deletions(-)
diff --git a/drivers/media/platform/mx2_emmaprp.c b/drivers/media/platform/mx2_emmaprp.c index e68d271b10af..8354ad20865a 100644 --- a/drivers/media/platform/mx2_emmaprp.c +++ b/drivers/media/platform/mx2_emmaprp.c @@ -288,7 +288,7 @@ static void emmaprp_device_run(void *priv) { struct emmaprp_ctx *ctx = priv; struct emmaprp_q_data *s_q_data, *d_q_data; - struct vb2_buffer *src_buf, *dst_buf; + struct vb2_v4l2_buffer *src_buf, *dst_buf; struct emmaprp_dev *pcdev = ctx->dev; unsigned int s_width, s_height; unsigned int d_width, d_height; @@ -308,8 +308,8 @@ static void emmaprp_device_run(void *priv) d_height = d_q_data->height; d_size = d_width * d_height;
- p_in = vb2_dma_contig_plane_dma_addr(src_buf, 0); - p_out = vb2_dma_contig_plane_dma_addr(dst_buf, 0); + p_in = vb2_dma_contig_plane_dma_addr(&src_buf->vb2_buf, 0); + p_out = vb2_dma_contig_plane_dma_addr(&dst_buf->vb2_buf, 0); if (!p_in || !p_out) { v4l2_err(&pcdev->v4l2_dev, "Acquiring kernel pointers to buffers failed\n");
From: Aurelien Jarno aurelien@aurel32.net
[ Upstream commit cc4b1242d7e3b42eed73881fc749944146493e4f ]
The preadv2 and pwritev2 syscalls are supposed to emulate the readv and writev syscalls when offset == -1. Therefore the compat code should check for offset before calling do_compat_preadv64 and do_compat_pwritev64. This is the case for the preadv2 and pwritev2 syscalls, but handling of offset == -1 is missing in their 64-bit equivalent.
This patch fixes that, calling do_compat_readv and do_compat_writev when offset == -1. This fixes the following glibc tests on x32: - misc/tst-preadvwritev2 - misc/tst-preadvwritev64v2
Cc: Alexander Viro viro@zeniv.linux.org.uk Cc: H.J. Lu hjl.tools@gmail.com Signed-off-by: Aurelien Jarno aurelien@aurel32.net Signed-off-by: Al Viro viro@zeniv.linux.org.uk Signed-off-by: Sasha Levin sashal@kernel.org --- fs/read_write.c | 6 ++++++ 1 file changed, 6 insertions(+)
diff --git a/fs/read_write.c b/fs/read_write.c index 9819f7c6c8c5..6ab67b860159 100644 --- a/fs/read_write.c +++ b/fs/read_write.c @@ -1204,6 +1204,9 @@ COMPAT_SYSCALL_DEFINE5(preadv64v2, unsigned long, fd, const struct compat_iovec __user *,vec, unsigned long, vlen, loff_t, pos, int, flags) { + if (pos == -1) + return do_compat_readv(fd, vec, vlen, flags); + return do_compat_preadv64(fd, vec, vlen, pos, flags); } #endif @@ -1310,6 +1313,9 @@ COMPAT_SYSCALL_DEFINE5(pwritev64v2, unsigned long, fd, const struct compat_iovec __user *,vec, unsigned long, vlen, loff_t, pos, int, flags) { + if (pos == -1) + return do_compat_writev(fd, vec, vlen, flags); + return do_compat_pwritev64(fd, vec, vlen, pos, flags); } #endif
From: Hong Liu hong.liu@intel.com
[ Upstream commit 0d28f49412405d87d3aae83da255070a46e67627 ]
When performing a warm reset in ishtp bus driver, the ishtp_cl_device will not be removed, its fw_client still points to the already freed ishtp_device.fw_clients array.
Later after driver finishing ishtp client enumeration, this dangling pointer may cause driver to bind the wrong ishtp_cl_device to the new client, causing wrong callback to be called for messages intended for the new client.
This helps in development of firmware where frequent switching of firmwares is required without Linux reboot.
Signed-off-by: Hong Liu hong.liu@intel.com Tested-by: Hongyan Song hongyan.song@intel.com Acked-by: Srinivas Pandruvada srinivas.pandruvada@linux.intel.com Signed-off-by: Jiri Kosina jkosina@suse.cz Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/hid/intel-ish-hid/ishtp/bus.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/hid/intel-ish-hid/ishtp/bus.c b/drivers/hid/intel-ish-hid/ishtp/bus.c index 256521509d20..0de18c76f8d4 100644 --- a/drivers/hid/intel-ish-hid/ishtp/bus.c +++ b/drivers/hid/intel-ish-hid/ishtp/bus.c @@ -628,7 +628,8 @@ int ishtp_cl_device_bind(struct ishtp_cl *cl) spin_lock_irqsave(&cl->dev->device_list_lock, flags); list_for_each_entry(cl_device, &cl->dev->device_list, device_link) { - if (cl_device->fw_client->client_id == cl->fw_client_id) { + if (cl_device->fw_client && + cl_device->fw_client->client_id == cl->fw_client_id) { cl->device = cl_device; rv = 0; break; @@ -688,6 +689,7 @@ void ishtp_bus_remove_all_clients(struct ishtp_device *ishtp_dev, spin_lock_irqsave(&ishtp_dev->device_list_lock, flags); list_for_each_entry_safe(cl_device, n, &ishtp_dev->device_list, device_link) { + cl_device->fw_client = NULL; if (warm_reset && cl_device->reference_count) continue;
From: Michal Kazior michal@plume.com
[ Upstream commit 5ddb0869bfc1bca6cfc592c74c64a026f936638c ]
I've stumbled upon a kernel crash and the logs pointed me towards the lp5562 driver:
<4>[306013.841294] lp5562 0-0030: Direct firmware load for lp5562 failed with error -2 <4>[306013.894990] lp5562 0-0030: Falling back to user helper ... <3>[306073.924886] lp5562 0-0030: firmware request failed <1>[306073.939456] Unable to handle kernel NULL pointer dereference at virtual address 00000000 <4>[306074.251011] PC is at _raw_spin_lock+0x1c/0x58 <4>[306074.255539] LR is at release_firmware+0x6c/0x138 ...
After taking a look I noticed firmware_release() could be called with either NULL or a dangling pointer.
Fixes: 10c06d178df11 ("leds-lp55xx: support firmware interface") Signed-off-by: Michal Kazior michal@plume.com Signed-off-by: Jacek Anaszewski jacek.anaszewski@gmail.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/leds/leds-lp55xx-common.c | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-)
diff --git a/drivers/leds/leds-lp55xx-common.c b/drivers/leds/leds-lp55xx-common.c index 5377f22ff994..e2655953667c 100644 --- a/drivers/leds/leds-lp55xx-common.c +++ b/drivers/leds/leds-lp55xx-common.c @@ -201,7 +201,7 @@ static void lp55xx_firmware_loaded(const struct firmware *fw, void *context)
if (!fw) { dev_err(dev, "firmware request failed\n"); - goto out; + return; }
/* handling firmware data is chip dependent */ @@ -214,9 +214,9 @@ static void lp55xx_firmware_loaded(const struct firmware *fw, void *context)
mutex_unlock(&chip->lock);
-out: /* firmware should be released for other channel use */ release_firmware(chip->fw); + chip->fw = NULL; }
static int lp55xx_request_firmware(struct lp55xx_chip *chip)
From: Sara Sharon sara.sharon@intel.com
[ Upstream commit c6ac9f9fb98851f47b978a9476594fc3c477a34d ]
Allocator swaps the pending requests with 0 when it starts working. This means that relying on it n RX path to decide if to move to emergency is not always a good idea, since it may be zero, but there are still a lot of unallocated RBs in the system. Change allocator to decrement the pending requests on real time. It is more expensive since it accesses the atomic variable more times, but it gives the RX path a better idea of the system's status.
Reported-by: Ilan Peer ilan.peer@intel.com Signed-off-by: Sara Sharon sara.sharon@intel.com Fixes: 868a1e863f95 ("iwlwifi: pcie: avoid empty free RB queue") Signed-off-by: Luca Coelho luciano.coelho@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/intel/iwlwifi/pcie/rx.c | 11 ++++++++--- 1 file changed, 8 insertions(+), 3 deletions(-)
diff --git a/drivers/net/wireless/intel/iwlwifi/pcie/rx.c b/drivers/net/wireless/intel/iwlwifi/pcie/rx.c index e58a50d31d96..c21f8bd32d08 100644 --- a/drivers/net/wireless/intel/iwlwifi/pcie/rx.c +++ b/drivers/net/wireless/intel/iwlwifi/pcie/rx.c @@ -475,7 +475,7 @@ static void iwl_pcie_rx_allocator(struct iwl_trans *trans) struct iwl_trans_pcie *trans_pcie = IWL_TRANS_GET_PCIE_TRANS(trans); struct iwl_rb_allocator *rba = &trans_pcie->rba; struct list_head local_empty; - int pending = atomic_xchg(&rba->req_pending, 0); + int pending = atomic_read(&rba->req_pending);
IWL_DEBUG_RX(trans, "Pending allocation requests = %d\n", pending);
@@ -530,11 +530,13 @@ static void iwl_pcie_rx_allocator(struct iwl_trans *trans) i++; }
+ atomic_dec(&rba->req_pending); pending--; + if (!pending) { - pending = atomic_xchg(&rba->req_pending, 0); + pending = atomic_read(&rba->req_pending); IWL_DEBUG_RX(trans, - "Pending allocation requests = %d\n", + "Got more pending allocation requests = %d\n", pending); }
@@ -546,12 +548,15 @@ static void iwl_pcie_rx_allocator(struct iwl_trans *trans) spin_unlock(&rba->lock);
atomic_inc(&rba->req_ready); + }
spin_lock(&rba->lock); /* return unused rbds to the allocator empty list */ list_splice_tail(&local_empty, &rba->rbd_empty); spin_unlock(&rba->lock); + + IWL_DEBUG_RX(trans, "%s, exit.\n", __func__); }
/*
From: Hans de Goede hdegoede@redhat.com
[ Upstream commit cecf3e3e0803462335e25d083345682518097334 ]
This commit refactors the chassis-type detection introduced by commit 53fa1f6e8a59 ("ACPI / video: Only default only_lcd to true on Win8-ready _desktops_") (where desktop means anything without a builtin screen).
The DMI chassis_type is an unsigned integer, so rather then doing a whole bunch of string-compares on it, convert it to an int and feed the result to a switch case.
Note the switch case uses hex values, this is done because the spec uses hex values too. This changes the check for "Main Server Chassis" from checking for 11 decimal to 11 hexadecimal, this is a bug fix, the original check for 11 decimal was wrong.
Fixes: 53fa1f6e8a59 ("ACPI / video: Only default only_lcd to true ...") Signed-off-by: Hans de Goede hdegoede@redhat.com [ rjw: Drop redundant return statements ] Signed-off-by: Rafael J. Wysocki rafael.j.wysocki@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/acpi/acpi_video.c | 19 +++++++++++++------ 1 file changed, 13 insertions(+), 6 deletions(-)
diff --git a/drivers/acpi/acpi_video.c b/drivers/acpi/acpi_video.c index 667dc5c86fef..d79e38abd6d9 100644 --- a/drivers/acpi/acpi_video.c +++ b/drivers/acpi/acpi_video.c @@ -2069,21 +2069,28 @@ static int __init intel_opregion_present(void) return opregion; }
+/* Check if the chassis-type indicates there is no builtin LCD panel */ static bool dmi_is_desktop(void) { const char *chassis_type; + unsigned long type;
chassis_type = dmi_get_system_info(DMI_CHASSIS_TYPE); if (!chassis_type) return false;
- if (!strcmp(chassis_type, "3") || /* 3: Desktop */ - !strcmp(chassis_type, "4") || /* 4: Low Profile Desktop */ - !strcmp(chassis_type, "5") || /* 5: Pizza Box */ - !strcmp(chassis_type, "6") || /* 6: Mini Tower */ - !strcmp(chassis_type, "7") || /* 7: Tower */ - !strcmp(chassis_type, "11")) /* 11: Main Server Chassis */ + if (kstrtoul(chassis_type, 10, &type) != 0) + return false; + + switch (type) { + case 0x03: /* Desktop */ + case 0x04: /* Low Profile Desktop */ + case 0x05: /* Pizza Box */ + case 0x06: /* Mini Tower */ + case 0x07: /* Tower */ + case 0x11: /* Main Server Chassis */ return true; + }
return false; }
From: Andrea Righi righi.andrea@gmail.com
[ Upstream commit 02106f883cd745523f7766d90a739f983f19e650 ]
Since kprobe breakpoing handler is using bsearch(), probing on this routine can cause recursive breakpoint problem.
int3 ->do_int3() ->ftrace_int3_handler() ->ftrace_location() ->ftrace_location_range() ->bsearch() -> int3
Prohibit probing on bsearch().
Signed-off-by: Andrea Righi righi.andrea@gmail.com Acked-by: Masami Hiramatsu mhiramat@kernel.org Cc: Alexander Shishkin alexander.shishkin@linux.intel.com Cc: Arnaldo Carvalho de Melo acme@redhat.com Cc: Jiri Olsa jolsa@redhat.com Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Mathieu Desnoyers mathieu.desnoyers@efficios.com Cc: Peter Zijlstra peterz@infradead.org Cc: Steven Rostedt rostedt@goodmis.org Cc: Thomas Gleixner tglx@linutronix.de Link: http://lkml.kernel.org/r/154998813406.31052.8791425358974650922.stgit@devbox Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- lib/bsearch.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/lib/bsearch.c b/lib/bsearch.c index e33c179089db..d50048446b77 100644 --- a/lib/bsearch.c +++ b/lib/bsearch.c @@ -11,6 +11,7 @@
#include <linux/export.h> #include <linux/bsearch.h> +#include <linux/kprobes.h>
/* * bsearch - binary search an array of elements @@ -51,3 +52,4 @@ void *bsearch(const void *key, const void *base, size_t num, size_t size, return NULL; } EXPORT_SYMBOL(bsearch); +NOKPROBE_SYMBOL(bsearch);
From: Nathan Chancellor natechancellor@gmail.com
[ Upstream commit de9c0d49d85dc563549972edc5589d195cd5e859 ]
While building arm32 allyesconfig, I ran into the following errors:
arch/arm/lib/xor-neon.c:17:2: error: You should compile this file with '-mfloat-abi=softfp -mfpu=neon'
In file included from lib/raid6/neon1.c:27: /home/nathan/cbl/prebuilt/lib/clang/8.0.0/include/arm_neon.h:28:2: error: "NEON support not enabled"
Building V=1 showed NEON_FLAGS getting passed along to Clang but __ARM_NEON__ was not getting defined. Ultimately, it boils down to Clang only defining __ARM_NEON__ when targeting armv7, rather than armv6k, which is the '-march' value for allyesconfig.
From lib/Basic/Targets/ARM.cpp in the Clang source:
// This only gets set when Neon instructions are actually available, unlike // the VFP define, hence the soft float and arch check. This is subtly // different from gcc, we follow the intent which was that it should be set // when Neon instructions are actually available. if ((FPU & NeonFPU) && !SoftFloat && ArchVersion >= 7) { Builder.defineMacro("__ARM_NEON", "1"); Builder.defineMacro("__ARM_NEON__"); // current AArch32 NEON implementations do not support double-precision // floating-point even when it is present in VFP. Builder.defineMacro("__ARM_NEON_FP", "0x" + Twine::utohexstr(HW_FP & ~HW_FP_DP)); }
Ard Biesheuvel recommended explicitly adding '-march=armv7-a' at the beginning of the NEON_FLAGS definitions so that __ARM_NEON__ always gets definined by Clang. This doesn't functionally change anything because that code will only run where NEON is supported, which is implicitly armv7.
Link: https://github.com/ClangBuiltLinux/linux/issues/287
Suggested-by: Ard Biesheuvel ard.biesheuvel@linaro.org Signed-off-by: Nathan Chancellor natechancellor@gmail.com Acked-by: Nicolas Pitre nico@linaro.org Reviewed-by: Nick Desaulniers ndesaulniers@google.com Reviewed-by: Stefan Agner stefan@agner.ch Signed-off-by: Russell King rmk+kernel@armlinux.org.uk Signed-off-by: Sasha Levin sashal@kernel.org --- Documentation/arm/kernel_mode_neon.txt | 4 ++-- arch/arm/lib/Makefile | 2 +- arch/arm/lib/xor-neon.c | 2 +- lib/raid6/Makefile | 2 +- 4 files changed, 5 insertions(+), 5 deletions(-)
diff --git a/Documentation/arm/kernel_mode_neon.txt b/Documentation/arm/kernel_mode_neon.txt index 525452726d31..b9e060c5b61e 100644 --- a/Documentation/arm/kernel_mode_neon.txt +++ b/Documentation/arm/kernel_mode_neon.txt @@ -6,7 +6,7 @@ TL;DR summary * Use only NEON instructions, or VFP instructions that don't rely on support code * Isolate your NEON code in a separate compilation unit, and compile it with - '-mfpu=neon -mfloat-abi=softfp' + '-march=armv7-a -mfpu=neon -mfloat-abi=softfp' * Put kernel_neon_begin() and kernel_neon_end() calls around the calls into your NEON code * Don't sleep in your NEON code, and be aware that it will be executed with @@ -87,7 +87,7 @@ instructions appearing in unexpected places if no special care is taken. Therefore, the recommended and only supported way of using NEON/VFP in the kernel is by adhering to the following rules: * isolate the NEON code in a separate compilation unit and compile it with - '-mfpu=neon -mfloat-abi=softfp'; + '-march=armv7-a -mfpu=neon -mfloat-abi=softfp'; * issue the calls to kernel_neon_begin(), kernel_neon_end() as well as the calls into the unit containing the NEON code from a compilation unit which is *not* built with the GCC flag '-mfpu=neon' set. diff --git a/arch/arm/lib/Makefile b/arch/arm/lib/Makefile index 27f4d96258a2..b3ecffb76c3f 100644 --- a/arch/arm/lib/Makefile +++ b/arch/arm/lib/Makefile @@ -38,7 +38,7 @@ $(obj)/csumpartialcopy.o: $(obj)/csumpartialcopygeneric.S $(obj)/csumpartialcopyuser.o: $(obj)/csumpartialcopygeneric.S
ifeq ($(CONFIG_KERNEL_MODE_NEON),y) - NEON_FLAGS := -mfloat-abi=softfp -mfpu=neon + NEON_FLAGS := -march=armv7-a -mfloat-abi=softfp -mfpu=neon CFLAGS_xor-neon.o += $(NEON_FLAGS) obj-$(CONFIG_XOR_BLOCKS) += xor-neon.o endif diff --git a/arch/arm/lib/xor-neon.c b/arch/arm/lib/xor-neon.c index 2c40aeab3eaa..c691b901092f 100644 --- a/arch/arm/lib/xor-neon.c +++ b/arch/arm/lib/xor-neon.c @@ -14,7 +14,7 @@ MODULE_LICENSE("GPL");
#ifndef __ARM_NEON__ -#error You should compile this file with '-mfloat-abi=softfp -mfpu=neon' +#error You should compile this file with '-march=armv7-a -mfloat-abi=softfp -mfpu=neon' #endif
/* diff --git a/lib/raid6/Makefile b/lib/raid6/Makefile index 3057011f5599..10ca69475611 100644 --- a/lib/raid6/Makefile +++ b/lib/raid6/Makefile @@ -24,7 +24,7 @@ endif ifeq ($(CONFIG_KERNEL_MODE_NEON),y) NEON_FLAGS := -ffreestanding ifeq ($(ARCH),arm) -NEON_FLAGS += -mfloat-abi=softfp -mfpu=neon +NEON_FLAGS += -march=armv7-a -mfloat-abi=softfp -mfpu=neon endif ifeq ($(ARCH),arm64) CFLAGS_REMOVE_neon1.o += -mgeneral-regs-only
From: Ranjani Sridharan ranjani.sridharan@linux.intel.com
[ Upstream commit d9c0b2afe820fa3b3f8258a659daee2cc71ca3ef ]
BE dai links only have internal PCM's and their substream ops may not be set. Suspending these PCM's will result in their ops->trigger() being invoked and cause a kernel oops. So skip suspending PCM's if their ops are NULL.
[ NOTE: this change is required now for following the recent PCM core change to get rid of snd_pcm_suspend() call. Since DPCM BE takes the runtime carried from FE while keeping NULL ops, it can hit this bug. See details at: https://github.com/thesofproject/linux/pull/582 -- tiwai ]
Signed-off-by: Ranjani Sridharan ranjani.sridharan@linux.intel.com Signed-off-by: Pierre-Louis Bossart pierre-louis.bossart@linux.intel.com Signed-off-by: Takashi Iwai tiwai@suse.de Signed-off-by: Sasha Levin sashal@kernel.org --- sound/core/pcm_native.c | 8 ++++++++ 1 file changed, 8 insertions(+)
diff --git a/sound/core/pcm_native.c b/sound/core/pcm_native.c index 3586ab41dec4..4719f7f42aa8 100644 --- a/sound/core/pcm_native.c +++ b/sound/core/pcm_native.c @@ -1339,6 +1339,14 @@ int snd_pcm_suspend_all(struct snd_pcm *pcm) /* FIXME: the open/close code should lock this as well */ if (substream->runtime == NULL) continue; + + /* + * Skip BE dai link PCM's that are internal and may + * not have their substream ops set. + */ + if (!substream->ops) + continue; + err = snd_pcm_suspend(substream); if (err < 0 && err != -EBUSY) return err;
From: John Stultz john.stultz@linaro.org
[ Upstream commit 54f64d5c983f939901dacc8cfc0983727c5c742e ]
Since the 5.0 merge window opened, I've been seeing frequent crashes on suspend and reboot with the trace:
[ 36.911170] Unable to handle kernel paging request at virtual address ffffff801153d660 [ 36.912769] Unable to handle kernel paging request at virtual address ffffff800004b564 ... [ 36.950666] Call trace: [ 36.950670] queued_spin_lock_slowpath+0x1cc/0x2c8 [ 36.950681] _raw_spin_lock_irqsave+0x64/0x78 [ 36.950692] complete+0x28/0x70 [ 36.950703] ffs_epfile_io_complete+0x3c/0x50 [ 36.950713] usb_gadget_giveback_request+0x34/0x108 [ 36.950721] dwc3_gadget_giveback+0x50/0x68 [ 36.950723] dwc3_thread_interrupt+0x358/0x1488 [ 36.950731] irq_thread_fn+0x30/0x88 [ 36.950734] irq_thread+0x114/0x1b0 [ 36.950739] kthread+0x104/0x130 [ 36.950747] ret_from_fork+0x10/0x1c
I isolated this down to in ffs_epfile_io(): https://git.kernel.org/pub/scm/linux/kernel/git/torvalds/linux.git/tree/driv...
Where the completion done is setup on the stack: DECLARE_COMPLETION_ONSTACK(done);
Then later we setup a request and queue it, and wait for it: if (unlikely(wait_for_completion_interruptible(&done))) { /* * To avoid race condition with ffs_epfile_io_complete, * dequeue the request first then check * status. usb_ep_dequeue API should guarantee no race * condition with req->complete callback. */ usb_ep_dequeue(ep->ep, req); interrupted = ep->status < 0; }
The problem is, that we end up being interrupted, dequeue the request, and exit.
But then the irq triggers and we try calling complete() on the context pointer which points to now random stack space, which results in the panic.
Alan Stern pointed out there is a bug here, in that the snippet above "assumes that usb_ep_dequeue() waits until the request has been completed." And that:
wait_for_completion(&done);
Is needed right after the usb_ep_dequeue().
Thus this patch implements that change. With it I no longer see the crashes on suspend or reboot.
This issue seems to have been uncovered by behavioral changes in the dwc3 driver in commit fec9095bdef4e ("usb: dwc3: gadget: remove wait_end_transfer").
Cc: Alan Stern stern@rowland.harvard.edu Cc: Felipe Balbi balbi@kernel.org Cc: Zeng Tao prime.zeng@hisilicon.com Cc: Jack Pham jackp@codeaurora.org Cc: Thinh Nguyen thinh.nguyen@synopsys.com Cc: Chen Yu chenyu56@huawei.com Cc: Jerry Zhang zhangjerry@google.com Cc: Lars-Peter Clausen lars@metafoo.de Cc: Vincent Pelletier plr.vincent@gmail.com Cc: Andrzej Pietrasiewicz andrzej.p@samsung.com Cc: Greg Kroah-Hartman gregkh@linuxfoundation.org Cc: Linux USB List linux-usb@vger.kernel.org Suggested-by: Alan Stern stern@rowland.harvard.edu Signed-off-by: John Stultz john.stultz@linaro.org Signed-off-by: Felipe Balbi felipe.balbi@linux.intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/usb/gadget/function/f_fs.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/usb/gadget/function/f_fs.c b/drivers/usb/gadget/function/f_fs.c index 04eb64381d92..927ac0ee09b7 100644 --- a/drivers/usb/gadget/function/f_fs.c +++ b/drivers/usb/gadget/function/f_fs.c @@ -1008,6 +1008,7 @@ static ssize_t ffs_epfile_io(struct file *file, struct ffs_io_data *io_data) * condition with req->complete callback. */ usb_ep_dequeue(ep->ep, req); + wait_for_completion(&done); interrupted = ep->status < 0; }
From: Coly Li colyli@suse.de
[ Upstream commit a91fbda49f746119828f7e8ad0f0aa2ab0578f65 ]
Cache set sysfs entry io_error_halflife is used to set c->error_decay. c->error_decay is in type unsigned int, and it is converted by strtoul_or_return(), therefore overflow to c->error_decay is possible for a large input value.
This patch fixes the overflow by using strtoul_safe_clamp() to convert input string to an unsigned long value in range [0, UINT_MAX], then divides by 88 and set it to c->error_decay.
Signed-off-by: Coly Li colyli@suse.de Signed-off-by: Jens Axboe axboe@kernel.dk Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/md/bcache/sysfs.c | 13 +++++++++++-- 1 file changed, 11 insertions(+), 2 deletions(-)
diff --git a/drivers/md/bcache/sysfs.c b/drivers/md/bcache/sysfs.c index 5a5c1f1bd8a5..87daccbbc61b 100644 --- a/drivers/md/bcache/sysfs.c +++ b/drivers/md/bcache/sysfs.c @@ -645,8 +645,17 @@ STORE(__bch_cache_set) c->error_limit = strtoul_or_return(buf) << IO_ERROR_SHIFT;
/* See count_io_errors() for why 88 */ - if (attr == &sysfs_io_error_halflife) - c->error_decay = strtoul_or_return(buf) / 88; + if (attr == &sysfs_io_error_halflife) { + unsigned long v = 0; + ssize_t ret; + + ret = strtoul_safe_clamp(buf, v, 0, UINT_MAX); + if (!ret) { + c->error_decay = v / 88; + return size; + } + return ret; + }
sysfs_strtoul(journal_delay_ms, c->journal_delay_ms); sysfs_strtoul(verify, c->verify);
From: Coly Li colyli@suse.de
[ Upstream commit 8c27a3953e92eb0b22dbb03d599f543a05f9574e ]
People may set sequential_cutoff of a cached device via sysfs file, but current code does not check input value overflow. E.g. if value 4294967295 (UINT_MAX) is written to file sequential_cutoff, its value is 4GB, but if 4294967296 (UINT_MAX + 1) is written into, its value will be 0. This is an unexpected behavior.
This patch replaces d_strtoi_h() by sysfs_strtoul_clamp() to convert input string to unsigned integer value, and limit its range in [0, UINT_MAX]. Then the input overflow can be fixed.
Signed-off-by: Coly Li colyli@suse.de Signed-off-by: Jens Axboe axboe@kernel.dk Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/md/bcache/sysfs.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/md/bcache/sysfs.c b/drivers/md/bcache/sysfs.c index 87daccbbc61b..463ce6757338 100644 --- a/drivers/md/bcache/sysfs.c +++ b/drivers/md/bcache/sysfs.c @@ -215,7 +215,9 @@ STORE(__cached_dev) d_strtoul(writeback_rate_d_term); d_strtoul_nonzero(writeback_rate_p_term_inverse);
- d_strtoi_h(sequential_cutoff); + sysfs_strtoul_clamp(sequential_cutoff, + dc->sequential_cutoff, + 0, UINT_MAX); d_strtoi_h(readahead);
if (attr == &sysfs_clear_stats)
From: Coly Li colyli@suse.de
[ Upstream commit 596b5a5dd1bc2fa019fdaaae522ef331deef927f ]
Currently sysfs_strtoul_clamp() is defined as, 82 #define sysfs_strtoul_clamp(file, var, min, max) \ 83 do { \ 84 if (attr == &sysfs_ ## file) \ 85 return strtoul_safe_clamp(buf, var, min, max) \ 86 ?: (ssize_t) size; \ 87 } while (0)
The problem is, if bit width of var is less then unsigned long, min and max may not protect var from integer overflow, because overflow happens in strtoul_safe_clamp() before checking min and max.
To fix such overflow in sysfs_strtoul_clamp(), to make min and max take effect, this patch adds an unsigned long variable, and uses it to macro strtoul_safe_clamp() to convert an unsigned long value in range defined by [min, max]. Then assign this value to var. By this method, if bit width of var is less than unsigned long, integer overflow won't happen before min and max are checking.
Now sysfs_strtoul_clamp() can properly handle smaller data type like unsigned int, of cause min and max should be defined in range of unsigned int too.
Signed-off-by: Coly Li colyli@suse.de Signed-off-by: Jens Axboe axboe@kernel.dk Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/md/bcache/sysfs.h | 13 ++++++++++--- 1 file changed, 10 insertions(+), 3 deletions(-)
diff --git a/drivers/md/bcache/sysfs.h b/drivers/md/bcache/sysfs.h index 0526fe92a683..e7a3c12aa66f 100644 --- a/drivers/md/bcache/sysfs.h +++ b/drivers/md/bcache/sysfs.h @@ -80,9 +80,16 @@ do { \
#define sysfs_strtoul_clamp(file, var, min, max) \ do { \ - if (attr == &sysfs_ ## file) \ - return strtoul_safe_clamp(buf, var, min, max) \ - ?: (ssize_t) size; \ + if (attr == &sysfs_ ## file) { \ + unsigned long v = 0; \ + ssize_t ret; \ + ret = strtoul_safe_clamp(buf, v, min, max); \ + if (!ret) { \ + var = v; \ + return size; \ + } \ + return ret; \ + } \ } while (0)
#define strtoul_or_return(cp) \
From: Thomas Gleixner tglx@linutronix.de
[ Upstream commit 1136b0728969901a091f0471968b2b76ed14d9ad ]
Waiman reported that on large systems with a large amount of interrupts the readout of /proc/stat takes a long time to sum up the interrupt statistics. In principle this is not a problem. but for unknown reasons some enterprise quality software reads /proc/stat with a high frequency.
The reason for this is that interrupt statistics are accounted per cpu. So the /proc/stat logic has to sum up the interrupt stats for each interrupt.
This can be largely avoided for interrupts which are not marked as 'PER_CPU' interrupts by simply adding a per interrupt summation counter which is incremented along with the per interrupt per cpu counter.
The PER_CPU interrupts need to avoid that and use only per cpu accounting because they share the interrupt number and the interrupt descriptor and concurrent updates would conflict or require unwanted synchronization.
Reported-by: Waiman Long longman@redhat.com Signed-off-by: Thomas Gleixner tglx@linutronix.de Reviewed-by: Waiman Long longman@redhat.com Reviewed-by: Marc Zyngier marc.zyngier@arm.com Reviewed-by: Davidlohr Bueso dbueso@suse.de Cc: Matthew Wilcox willy@infradead.org Cc: Andrew Morton akpm@linux-foundation.org Cc: Alexey Dobriyan adobriyan@gmail.com Cc: Kees Cook keescook@chromium.org Cc: linux-fsdevel@vger.kernel.org Cc: Davidlohr Bueso dave@stgolabs.net Cc: Miklos Szeredi miklos@szeredi.hu Cc: Daniel Colascione dancol@google.com Cc: Dave Chinner david@fromorbit.com Cc: Randy Dunlap rdunlap@infradead.org Link: https://lkml.kernel.org/r/20190208135020.925487496@linutronix.de
8<-------------
v2: Undo the unintentional layout change of struct irq_desc.
include/linux/irqdesc.h | 1 + kernel/irq/chip.c | 12 ++++++++++-- kernel/irq/internals.h | 8 +++++++- kernel/irq/irqdesc.c | 7 ++++++- 4 files changed, 24 insertions(+), 4 deletions(-)
Signed-off-by: Sasha Levin sashal@kernel.org --- include/linux/irqdesc.h | 1 + kernel/irq/chip.c | 12 ++++++++++-- kernel/irq/internals.h | 8 +++++++- kernel/irq/irqdesc.c | 7 ++++++- 4 files changed, 24 insertions(+), 4 deletions(-)
diff --git a/include/linux/irqdesc.h b/include/linux/irqdesc.h index c9be57931b58..bb5547a83daf 100644 --- a/include/linux/irqdesc.h +++ b/include/linux/irqdesc.h @@ -61,6 +61,7 @@ struct irq_desc { unsigned int core_internal_state__do_not_mess_with_it; unsigned int depth; /* nested irq disables */ unsigned int wake_depth; /* nested wake enables */ + unsigned int tot_count; unsigned int irq_count; /* For detecting broken IRQs */ unsigned long last_unhandled; /* Aging timer for unhandled count */ unsigned int irqs_unhandled; diff --git a/kernel/irq/chip.c b/kernel/irq/chip.c index f30110e1b8c9..9e745cc0726d 100644 --- a/kernel/irq/chip.c +++ b/kernel/irq/chip.c @@ -729,7 +729,11 @@ void handle_percpu_irq(struct irq_desc *desc) { struct irq_chip *chip = irq_desc_get_chip(desc);
- kstat_incr_irqs_this_cpu(desc); + /* + * PER CPU interrupts are not serialized. Do not touch + * desc->tot_count. + */ + __kstat_incr_irqs_this_cpu(desc);
if (chip->irq_ack) chip->irq_ack(&desc->irq_data); @@ -758,7 +762,11 @@ void handle_percpu_devid_irq(struct irq_desc *desc) unsigned int irq = irq_desc_get_irq(desc); irqreturn_t res;
- kstat_incr_irqs_this_cpu(desc); + /* + * PER CPU interrupts are not serialized. Do not touch + * desc->tot_count. + */ + __kstat_incr_irqs_this_cpu(desc);
if (chip->irq_ack) chip->irq_ack(&desc->irq_data); diff --git a/kernel/irq/internals.h b/kernel/irq/internals.h index bc226e783bd2..22e3f29a30d8 100644 --- a/kernel/irq/internals.h +++ b/kernel/irq/internals.h @@ -199,12 +199,18 @@ static inline bool irqd_has_set(struct irq_data *d, unsigned int mask)
#undef __irqd_to_state
-static inline void kstat_incr_irqs_this_cpu(struct irq_desc *desc) +static inline void __kstat_incr_irqs_this_cpu(struct irq_desc *desc) { __this_cpu_inc(*desc->kstat_irqs); __this_cpu_inc(kstat.irqs_sum); }
+static inline void kstat_incr_irqs_this_cpu(struct irq_desc *desc) +{ + __kstat_incr_irqs_this_cpu(desc); + desc->tot_count++; +} + static inline int irq_desc_get_node(struct irq_desc *desc) { return irq_common_data_get_node(&desc->irq_common_data); diff --git a/kernel/irq/irqdesc.c b/kernel/irq/irqdesc.c index 77977f55dff7..5e0ea17d01a6 100644 --- a/kernel/irq/irqdesc.c +++ b/kernel/irq/irqdesc.c @@ -109,6 +109,7 @@ static void desc_set_defaults(unsigned int irq, struct irq_desc *desc, int node, desc->depth = 1; desc->irq_count = 0; desc->irqs_unhandled = 0; + desc->tot_count = 0; desc->name = NULL; desc->owner = owner; for_each_possible_cpu(cpu) @@ -880,11 +881,15 @@ unsigned int kstat_irqs_cpu(unsigned int irq, int cpu) unsigned int kstat_irqs(unsigned int irq) { struct irq_desc *desc = irq_to_desc(irq); - int cpu; unsigned int sum = 0; + int cpu;
if (!desc || !desc->kstat_irqs) return 0; + if (!irq_settings_is_per_cpu_devid(desc) && + !irq_settings_is_per_cpu(desc)) + return desc->tot_count; + for_each_possible_cpu(cpu) sum += *per_cpu_ptr(desc->kstat_irqs, cpu); return sum;
From: Raju Rangoju rajur@chelsio.com
[ Upstream commit f368ff188ae4b3ef6f740a15999ea0373261b619 ]
When an application aborts the connection by moving QP from RTS to ERROR, then iw_cxgb4's modify_rc_qp() RTS->ERROR logic sets the *srqidxp to 0 via t4_set_wq_in_error(&qhp->wq, 0), and aborts the connection by calling c4iw_ep_disconnect().
c4iw_ep_disconnect() does the following: 1. sends up a close_complete_upcall(ep, -ECONNRESET) to libcxgb4. 2. sends abort request CPL to hw.
But, since the close_complete_upcall() is sent before sending the ABORT_REQ to hw, libcxgb4 would fail to release the srqidx if the connection holds one. Because, the srqidx is passed up to libcxgb4 only after corresponding ABORT_RPL is processed by kernel in abort_rpl().
This patch handle the corner-case by moving the call to close_complete_upcall() from c4iw_ep_disconnect() to abort_rpl(). So that libcxgb4 is notified about the -ECONNRESET only after abort_rpl(), and libcxgb4 can relinquish the srqidx properly.
Signed-off-by: Raju Rangoju rajur@chelsio.com Signed-off-by: Jason Gunthorpe jgg@mellanox.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/infiniband/hw/cxgb4/cm.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/drivers/infiniband/hw/cxgb4/cm.c b/drivers/infiniband/hw/cxgb4/cm.c index dd18b74cd01d..a2322b2dbd82 100644 --- a/drivers/infiniband/hw/cxgb4/cm.c +++ b/drivers/infiniband/hw/cxgb4/cm.c @@ -1872,8 +1872,10 @@ static int abort_rpl(struct c4iw_dev *dev, struct sk_buff *skb) } mutex_unlock(&ep->com.mutex);
- if (release) + if (release) { + close_complete_upcall(ep, -ECONNRESET); release_ep_resources(ep); + } c4iw_put_ep(&ep->com); return 0; } @@ -3567,7 +3569,6 @@ int c4iw_ep_disconnect(struct c4iw_ep *ep, int abrupt, gfp_t gfp) if (close) { if (abrupt) { set_bit(EP_DISC_ABORT, &ep->com.history); - close_complete_upcall(ep, -ECONNRESET); ret = send_abort(ep); } else { set_bit(EP_DISC_CLOSE, &ep->com.history);
From: Manfred Schlaegl manfred.schlaegl@ginzinger.com
[ Upstream commit a5399db139cb3ad9b8502d8b1bd02da9ce0b9df0 ]
There is no clipping on the x or y axis for logos larger that the framebuffer size. Therefore: a logo bigger than screen size leads to invalid memory access:
[ 1.254664] Backtrace: [ 1.254728] [<c02714e0>] (cfb_imageblit) from [<c026184c>] (fb_show_logo+0x620/0x684) [ 1.254763] r10:00000003 r9:00027fd8 r8:c6a40000 r7:c6a36e50 r6:00000000 r5:c06b81e4 [ 1.254774] r4:c6a3e800 [ 1.254810] [<c026122c>] (fb_show_logo) from [<c026c1e4>] (fbcon_switch+0x3fc/0x46c) [ 1.254842] r10:c6a3e824 r9:c6a3e800 r8:00000000 r7:c6a0c000 r6:c070b014 r5:c6a3e800 [ 1.254852] r4:c6808c00 [ 1.254889] [<c026bde8>] (fbcon_switch) from [<c029c8f8>] (redraw_screen+0xf0/0x1e8) [ 1.254918] r10:00000000 r9:00000000 r8:00000000 r7:00000000 r6:c070d5a0 r5:00000080 [ 1.254928] r4:c6808c00 [ 1.254961] [<c029c808>] (redraw_screen) from [<c029d264>] (do_bind_con_driver+0x194/0x2e4) [ 1.254991] r9:00000000 r8:00000000 r7:00000014 r6:c070d5a0 r5:c070d5a0 r4:c070d5a0
So prevent displaying a logo bigger than screen size and avoid invalid memory access.
Signed-off-by: Manfred Schlaegl manfred.schlaegl@ginzinger.com Signed-off-by: Martin Kepplinger martin.kepplinger@ginzinger.com Cc: Daniel Vetter daniel.vetter@ffwll.ch Signed-off-by: Bartlomiej Zolnierkiewicz b.zolnierkie@samsung.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/video/fbdev/core/fbmem.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/drivers/video/fbdev/core/fbmem.c b/drivers/video/fbdev/core/fbmem.c index a1d93151c059..c928190666ac 100644 --- a/drivers/video/fbdev/core/fbmem.c +++ b/drivers/video/fbdev/core/fbmem.c @@ -425,6 +425,9 @@ static void fb_do_show_logo(struct fb_info *info, struct fb_image *image, { unsigned int x;
+ if (image->width > info->var.xres || image->height > info->var.yres) + return; + if (rotate == FB_ROTATE_UR) { for (x = 0; x < num && image->dx + image->width <= info->var.xres;
From: Guenter Roeck linux@roeck-us.net
[ Upstream commit f25191bb322dec8fa2979ecb8235643aa42470e1 ]
The following traceback is sometimes seen when booting an image in qemu:
[ 54.608293] cdrom: Uniform CD-ROM driver Revision: 3.20 [ 54.611085] Fusion MPT base driver 3.04.20 [ 54.611877] Copyright (c) 1999-2008 LSI Corporation [ 54.616234] Fusion MPT SAS Host driver 3.04.20 [ 54.635139] sysctl duplicate entry: /dev/cdrom//info [ 54.639578] CPU: 0 PID: 266 Comm: kworker/u4:5 Not tainted 5.0.0-rc5 #1 [ 54.639578] Hardware name: QEMU Standard PC (Q35 + ICH9, 2009), BIOS 0.0.0 02/06/2015 [ 54.641273] Workqueue: events_unbound async_run_entry_fn [ 54.641273] Call Trace: [ 54.641273] dump_stack+0x67/0x90 [ 54.641273] __register_sysctl_table+0x50b/0x570 [ 54.641273] ? rcu_read_lock_sched_held+0x6f/0x80 [ 54.641273] ? kmem_cache_alloc_trace+0x1c7/0x1f0 [ 54.646814] __register_sysctl_paths+0x1c8/0x1f0 [ 54.646814] cdrom_sysctl_register.part.7+0xc/0x5f [ 54.646814] register_cdrom.cold.24+0x2a/0x33 [ 54.646814] sr_probe+0x4bd/0x580 [ 54.646814] ? __driver_attach+0xd0/0xd0 [ 54.646814] really_probe+0xd6/0x260 [ 54.646814] ? __driver_attach+0xd0/0xd0 [ 54.646814] driver_probe_device+0x4a/0xb0 [ 54.646814] ? __driver_attach+0xd0/0xd0 [ 54.646814] bus_for_each_drv+0x73/0xc0 [ 54.646814] __device_attach+0xd6/0x130 [ 54.646814] bus_probe_device+0x9a/0xb0 [ 54.646814] device_add+0x40c/0x670 [ 54.646814] ? __pm_runtime_resume+0x4f/0x80 [ 54.646814] scsi_sysfs_add_sdev+0x81/0x290 [ 54.646814] scsi_probe_and_add_lun+0x888/0xc00 [ 54.646814] ? scsi_autopm_get_host+0x21/0x40 [ 54.646814] __scsi_add_device+0x116/0x130 [ 54.646814] ata_scsi_scan_host+0x93/0x1c0 [ 54.646814] async_run_entry_fn+0x34/0x100 [ 54.646814] process_one_work+0x237/0x5e0 [ 54.646814] worker_thread+0x37/0x380 [ 54.646814] ? rescuer_thread+0x360/0x360 [ 54.646814] kthread+0x118/0x130 [ 54.646814] ? kthread_create_on_node+0x60/0x60 [ 54.646814] ret_from_fork+0x3a/0x50
The only sensible explanation is that cdrom_sysctl_register() is called twice, once from the module init function and once from register_cdrom(). cdrom_sysctl_register() is not mutex protected and may happily execute twice if the second call is made before the first call is complete.
Use a static atomic to ensure that the function is executed exactly once.
Signed-off-by: Guenter Roeck linux@roeck-us.net Signed-off-by: Jens Axboe axboe@kernel.dk Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/cdrom/cdrom.c | 7 +++---- 1 file changed, 3 insertions(+), 4 deletions(-)
diff --git a/drivers/cdrom/cdrom.c b/drivers/cdrom/cdrom.c index ff4280800cd0..a46f188f679e 100644 --- a/drivers/cdrom/cdrom.c +++ b/drivers/cdrom/cdrom.c @@ -265,6 +265,7 @@ /* #define ERRLOGMASK (CD_WARNING|CD_OPEN|CD_COUNT_TRACKS|CD_CLOSE) */ /* #define ERRLOGMASK (CD_WARNING|CD_REG_UNREG|CD_DO_IOCTL|CD_OPEN|CD_CLOSE|CD_COUNT_TRACKS) */
+#include <linux/atomic.h> #include <linux/module.h> #include <linux/fs.h> #include <linux/major.h> @@ -3683,9 +3684,9 @@ static struct ctl_table_header *cdrom_sysctl_header;
static void cdrom_sysctl_register(void) { - static int initialized; + static atomic_t initialized = ATOMIC_INIT(0);
- if (initialized == 1) + if (!atomic_add_unless(&initialized, 1, 1)) return;
cdrom_sysctl_header = register_sysctl_table(cdrom_root_table); @@ -3696,8 +3697,6 @@ static void cdrom_sysctl_register(void) cdrom_sysctl_settings.debug = debug; cdrom_sysctl_settings.lock = lockdoor; cdrom_sysctl_settings.check = check_media_type; - - initialized = 1; }
static void cdrom_sysctl_unregister(void)
From: Konstantin Khlebnikov khlebnikov@yandex-team.ru
[ Upstream commit 0f9e980bf5ee1a97e2e401c846b2af989eb21c61 ]
I'm seeing series of e1000e resets (sometimes endless) at system boot if something generates tx traffic at this time. In my case this is netconsole who sends message "e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames" from e1000e itself. As result e1000_watchdog_task sees used tx buffer while carrier is off and start this reset cycle again.
[ 17.794359] e1000e: eth1 NIC Link is Up 1000 Mbps Full Duplex, Flow Control: None [ 17.794714] IPv6: ADDRCONF(NETDEV_CHANGE): eth1: link becomes ready [ 22.936455] e1000e 0000:02:00.0 eth1: changing MTU from 1500 to 9000 [ 23.033336] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 26.102364] e1000e: eth1 NIC Link is Up 1000 Mbps Full Duplex, Flow Control: None [ 27.174495] 8021q: 802.1Q VLAN Support v1.8 [ 27.174513] 8021q: adding VLAN 0 to HW filter on device eth1 [ 30.671724] cgroup: cgroup: disabling cgroup2 socket matching due to net_prio or net_cls activation [ 30.898564] netpoll: netconsole: local port 6666 [ 30.898566] netpoll: netconsole: local IPv6 address 2a02:6b8:0:80b:beae:c5ff:fe28:23f8 [ 30.898567] netpoll: netconsole: interface 'eth1' [ 30.898568] netpoll: netconsole: remote port 6666 [ 30.898568] netpoll: netconsole: remote IPv6 address 2a02:6b8:b000:605c:e61d:2dff:fe03:3790 [ 30.898569] netpoll: netconsole: remote ethernet address b0:a8:6e:f4:ff:c0 [ 30.917747] console [netcon0] enabled [ 30.917749] netconsole: network logging started [ 31.453353] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 34.185730] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 34.321840] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 34.465822] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 34.597423] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 34.745417] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 34.877356] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 35.005441] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 35.157376] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 35.289362] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 35.417441] e1000e 0000:02:00.0: Some CPU C-states have been disabled in order to enable jumbo frames [ 37.790342] e1000e: eth1 NIC Link is Up 1000 Mbps Full Duplex, Flow Control: None
This patch flushes tx buffers only once when carrier is off rather than at each watchdog iteration.
Signed-off-by: Konstantin Khlebnikov khlebnikov@yandex-team.ru Tested-by: Aaron Brown aaron.f.brown@intel.com Signed-off-by: Jeff Kirsher jeffrey.t.kirsher@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/ethernet/intel/e1000e/netdev.c | 15 ++++++--------- 1 file changed, 6 insertions(+), 9 deletions(-)
diff --git a/drivers/net/ethernet/intel/e1000e/netdev.c b/drivers/net/ethernet/intel/e1000e/netdev.c index f56f8b6e2378..8bbedfc9c48f 100644 --- a/drivers/net/ethernet/intel/e1000e/netdev.c +++ b/drivers/net/ethernet/intel/e1000e/netdev.c @@ -5291,8 +5291,13 @@ static void e1000_watchdog_task(struct work_struct *work) /* 8000ES2LAN requires a Rx packet buffer work-around * on link down event; reset the controller to flush * the Rx packet buffer. + * + * If the link is lost the controller stops DMA, but + * if there is queued Tx work it cannot be done. So + * reset the controller to flush the Tx packet buffers. */ - if (adapter->flags & FLAG_RX_NEEDS_RESTART) + if ((adapter->flags & FLAG_RX_NEEDS_RESTART) || + e1000_desc_unused(tx_ring) + 1 < tx_ring->count) adapter->flags |= FLAG_RESTART_NOW; else pm_schedule_suspend(netdev->dev.parent, @@ -5315,14 +5320,6 @@ static void e1000_watchdog_task(struct work_struct *work) adapter->gotc_old = adapter->stats.gotc; spin_unlock(&adapter->stats64_lock);
- /* If the link is lost the controller stops DMA, but - * if there is queued Tx work it cannot be done. So - * reset the controller to flush the Tx packet buffers. - */ - if (!netif_carrier_ok(netdev) && - (e1000_desc_unused(tx_ring) + 1 < tx_ring->count)) - adapter->flags |= FLAG_RESTART_NOW; - /* If reset is necessary, do it outside of interrupt context. */ if (adapter->flags & FLAG_RESTART_NOW) { schedule_work(&adapter->reset_task);
From: wen yang yellowriver2010@hotmail.com
[ Upstream commit 11907e9d3533648615db08140e3045b829d2c141 ]
The of_find_device_by_node() takes a reference to the underlying device structure, we should release that reference.
Signed-off-by: Wen Yang yellowriver2010@hotmil.com Cc: Timur Tabi timur@kernel.org Cc: Nicolin Chen nicoleotsuka@gmail.com Cc: Xiubo Li Xiubo.Lee@gmail.com Cc: Fabio Estevam festevam@gmail.com Cc: Liam Girdwood lgirdwood@gmail.com Cc: Mark Brown broonie@kernel.org Cc: Jaroslav Kysela perex@perex.cz Cc: Takashi Iwai tiwai@suse.com Cc: alsa-devel@alsa-project.org Cc: linuxppc-dev@lists.ozlabs.org Cc: linux-kernel@vger.kernel.org Signed-off-by: Mark Brown broonie@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- sound/soc/fsl/fsl-asoc-card.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/sound/soc/fsl/fsl-asoc-card.c b/sound/soc/fsl/fsl-asoc-card.c index dffd549a0e2a..705d2524ec31 100644 --- a/sound/soc/fsl/fsl-asoc-card.c +++ b/sound/soc/fsl/fsl-asoc-card.c @@ -689,6 +689,7 @@ static int fsl_asoc_card_probe(struct platform_device *pdev) asrc_fail: of_node_put(asrc_np); of_node_put(codec_np); + put_device(&cpu_pdev->dev); fail: of_node_put(cpu_np);
From: Waiman Long longman@redhat.com
[ Upstream commit 71492580571467fb7177aade19c18ce7486267f5 ]
Tetsuo Handa had reported he saw an incorrect "downgrading a read lock" warning right after a previous lockdep warning. It is likely that the previous warning turned off lock debugging causing the lockdep to have inconsistency states leading to the lock downgrade warning.
Fix that by add a check for debug_locks at the beginning of __lock_downgrade().
Debugged-by: Tetsuo Handa penguin-kernel@i-love.sakura.ne.jp Reported-by: Tetsuo Handa penguin-kernel@i-love.sakura.ne.jp Reported-by: syzbot+53383ae265fb161ef488@syzkaller.appspotmail.com Signed-off-by: Waiman Long longman@redhat.com Signed-off-by: Peter Zijlstra (Intel) peterz@infradead.org Cc: Andrew Morton akpm@linux-foundation.org Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Paul E. McKenney paulmck@linux.vnet.ibm.com Cc: Peter Zijlstra peterz@infradead.org Cc: Thomas Gleixner tglx@linutronix.de Cc: Will Deacon will.deacon@arm.com Link: https://lkml.kernel.org/r/1547093005-26085-1-git-send-email-longman@redhat.c... Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- kernel/locking/lockdep.c | 3 +++ 1 file changed, 3 insertions(+)
diff --git a/kernel/locking/lockdep.c b/kernel/locking/lockdep.c index 26fc428476b9..d5b779d7e79f 100644 --- a/kernel/locking/lockdep.c +++ b/kernel/locking/lockdep.c @@ -3446,6 +3446,9 @@ __lock_set_class(struct lockdep_map *lock, const char *name, unsigned int depth; int i;
+ if (unlikely(!debug_locks)) + return 0; + depth = curr->lockdep_depth; /* * This function is about (re)setting the class of a held lock,
From: Ard Biesheuvel ard.biesheuvel@linaro.org
[ Upstream commit 5de0fef0230f3c8d75cff450a71740a7bf2db866 ]
The EFI memory attributes code cross-references the EFI memory map with the more granular EFI memory attributes table to ensure that they are in sync before applying the strict permissions to the regions it describes.
Since we always install virtual mappings for the EFI runtime regions to which these strict permissions apply, we currently perform a sanity check on the EFI memory descriptor, and ensure that the EFI_MEMORY_RUNTIME bit is set, and that the virtual address has been assigned.
However, in cases where a runtime region exists at physical address 0x0, and the virtual mapping equals the physical mapping, e.g., when running in mixed mode on x86, we encounter a memory descriptor with the runtime attribute and virtual address 0x0, and incorrectly draw the conclusion that a runtime region exists for which no virtual mapping was installed, and give up altogether. The consequence of this is that firmware mappings retain their read-write-execute permissions, making the system more vulnerable to attacks.
So let's only bail if the virtual address of 0x0 has been assigned to a physical region that does not reside at address 0x0.
Signed-off-by: Ard Biesheuvel ard.biesheuvel@linaro.org Acked-by: Sai Praneeth Prakhya sai.praneeth.prakhya@intel.com Cc: AKASHI Takahiro takahiro.akashi@linaro.org Cc: Alexander Graf agraf@suse.de Cc: Bjorn Andersson bjorn.andersson@linaro.org Cc: Borislav Petkov bp@alien8.de Cc: Heinrich Schuchardt xypron.glpk@gmx.de Cc: Jeffrey Hugo jhugo@codeaurora.org Cc: Lee Jones lee.jones@linaro.org Cc: Leif Lindholm leif.lindholm@linaro.org Cc: Linus Torvalds torvalds@linux-foundation.org Cc: Matt Fleming matt@codeblueprint.co.uk Cc: Peter Jones pjones@redhat.com Cc: Peter Zijlstra peterz@infradead.org Cc: Thomas Gleixner tglx@linutronix.de Cc: linux-efi@vger.kernel.org Fixes: 10f0d2f577053 ("efi: Implement generic support for the Memory ...") Link: http://lkml.kernel.org/r/20190202094119.13230-4-ard.biesheuvel@linaro.org Signed-off-by: Ingo Molnar mingo@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/firmware/efi/memattr.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/firmware/efi/memattr.c b/drivers/firmware/efi/memattr.c index 236004b9a50d..9faa09e7c31f 100644 --- a/drivers/firmware/efi/memattr.c +++ b/drivers/firmware/efi/memattr.c @@ -93,7 +93,7 @@ static bool entry_is_valid(const efi_memory_desc_t *in, efi_memory_desc_t *out)
if (!(md->attribute & EFI_MEMORY_RUNTIME)) continue; - if (md->virt_addr == 0) { + if (md->virt_addr == 0 && md->phys_addr != 0) { /* no virtual mapping has been installed by the stub */ break; }
From: Mathieu Malaterre malat@debian.org
[ Upstream commit 3e3380d0675d5e20b0af067d60cb947a4348bf9b ]
Improve the DTS files by removing all the leading "0x" and zeros to fix the following dtc warnings:
Warning (unit_address_format): Node /XXX unit name should not have leading "0x"
and
Warning (unit_address_format): Node /XXX unit name should not have leading 0s
Converted using the following command:
find . -type f ( -iname *.dts -o -iname *.dtsi ) -exec sed -i -e "s/@([0-9a-fA-FxX.;:#]+)\s*{/@\L\1 {/g" -e "s/@0x(.*) {/@\1 {/g" -e "s/@0+(.*) {/@\1 {/g" {} +
For simplicity, two sed expressions were used to solve each warnings separately.
To make the regex expression more robust a few other issues were resolved, namely setting unit-address to lower case, and adding a whitespace before the opening curly brace:
https://elinux.org/Device_Tree_Linux#Linux_conventions
This will solve as a side effect warning:
Warning (simple_bus_reg): Node /XXX@<UPPER> simple-bus unit address format error, expected "<lower>"
This is a follow up to commit 4c9847b7375a ("dt-bindings: Remove leading 0x from bindings notation")
Reported-by: David Daney ddaney@caviumnetworks.com Suggested-by: Rob Herring robh@kernel.org Signed-off-by: Mathieu Malaterre malat@debian.org [vzapolskiy: fixed commit message to pass checkpatch.pl test] Signed-off-by: Vladimir Zapolskiy vz@mleia.com Signed-off-by: Sasha Levin sashal@kernel.org --- arch/arm/boot/dts/lpc32xx.dtsi | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-)
diff --git a/arch/arm/boot/dts/lpc32xx.dtsi b/arch/arm/boot/dts/lpc32xx.dtsi index b5841fab51c1..0d20aadc78bb 100644 --- a/arch/arm/boot/dts/lpc32xx.dtsi +++ b/arch/arm/boot/dts/lpc32xx.dtsi @@ -230,7 +230,7 @@ status = "disabled"; };
- i2s1: i2s@2009C000 { + i2s1: i2s@2009c000 { compatible = "nxp,lpc3220-i2s"; reg = <0x2009C000 0x1000>; }; @@ -273,7 +273,7 @@ status = "disabled"; };
- i2c1: i2c@400A0000 { + i2c1: i2c@400a0000 { compatible = "nxp,pnx-i2c"; reg = <0x400A0000 0x100>; interrupt-parent = <&sic1>; @@ -284,7 +284,7 @@ clocks = <&clk LPC32XX_CLK_I2C1>; };
- i2c2: i2c@400A8000 { + i2c2: i2c@400a8000 { compatible = "nxp,pnx-i2c"; reg = <0x400A8000 0x100>; interrupt-parent = <&sic1>; @@ -295,7 +295,7 @@ clocks = <&clk LPC32XX_CLK_I2C2>; };
- mpwm: mpwm@400E8000 { + mpwm: mpwm@400e8000 { compatible = "nxp,lpc3220-motor-pwm"; reg = <0x400E8000 0x78>; status = "disabled"; @@ -394,7 +394,7 @@ #gpio-cells = <3>; /* bank, pin, flags */ };
- timer4: timer@4002C000 { + timer4: timer@4002c000 { compatible = "nxp,lpc3220-timer"; reg = <0x4002C000 0x1000>; interrupts = <3 IRQ_TYPE_LEVEL_LOW>; @@ -412,7 +412,7 @@ status = "disabled"; };
- watchdog: watchdog@4003C000 { + watchdog: watchdog@4003c000 { compatible = "nxp,pnx4008-wdt"; reg = <0x4003C000 0x1000>; clocks = <&clk LPC32XX_CLK_WDOG>; @@ -451,7 +451,7 @@ status = "disabled"; };
- timer1: timer@4004C000 { + timer1: timer@4004c000 { compatible = "nxp,lpc3220-timer"; reg = <0x4004C000 0x1000>; interrupts = <17 IRQ_TYPE_LEVEL_LOW>; @@ -475,14 +475,14 @@ status = "disabled"; };
- pwm1: pwm@4005C000 { + pwm1: pwm@4005c000 { compatible = "nxp,lpc3220-pwm"; reg = <0x4005C000 0x4>; clocks = <&clk LPC32XX_CLK_PWM1>; status = "disabled"; };
- pwm2: pwm@4005C004 { + pwm2: pwm@4005c004 { compatible = "nxp,lpc3220-pwm"; reg = <0x4005C004 0x4>; clocks = <&clk LPC32XX_CLK_PWM2>;
From: Alexey Khoroshilov khoroshilov@ispras.ru
[ Upstream commit 8cd09a3dd3e176c62da67efcd477a44a8d87185e ]
If of_platform_populate() fails in gsbi_probe(), gsbi->hclk is left undisabled.
Found by Linux Driver Verification project (linuxtesting.org).
Signed-off-by: Alexey Khoroshilov khoroshilov@ispras.ru Signed-off-by: Bjorn Andersson bjorn.andersson@linaro.org Signed-off-by: Andy Gross andy.gross@linaro.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/soc/qcom/qcom_gsbi.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
diff --git a/drivers/soc/qcom/qcom_gsbi.c b/drivers/soc/qcom/qcom_gsbi.c index 09c669e70d63..038abc377fdb 100644 --- a/drivers/soc/qcom/qcom_gsbi.c +++ b/drivers/soc/qcom/qcom_gsbi.c @@ -138,7 +138,7 @@ static int gsbi_probe(struct platform_device *pdev) struct resource *res; void __iomem *base; struct gsbi_info *gsbi; - int i; + int i, ret; u32 mask, gsbi_num; const struct crci_config *config = NULL;
@@ -221,7 +221,10 @@ static int gsbi_probe(struct platform_device *pdev)
platform_set_drvdata(pdev, gsbi);
- return of_platform_populate(node, NULL, NULL, &pdev->dev); + ret = of_platform_populate(node, NULL, NULL, &pdev->dev); + if (ret) + clk_disable_unprepare(gsbi->hclk); + return ret; }
static int gsbi_remove(struct platform_device *pdev)
From: Stanislaw Gruszka sgruszka@redhat.com
[ Upstream commit 3bd1505fed71d834f45e87b32ff07157fdda47e0 ]
As reported by Michael eeprom 0d is supported and work with the driver.
Dump of /sys/kernel/debug/ieee80211/phy1/mt7601u/eeprom_param with 0d EEPORM looks like this:
RSSI offset: 0 0 Reference temp: f9 LNA gain: 8 Reg channels: 1-14 Per rate power: raw:05 bw20:05 bw40:05 raw:05 bw20:05 bw40:05 raw:03 bw20:03 bw40:03 raw:03 bw20:03 bw40:03 raw:04 bw20:04 bw40:04 raw:00 bw20:00 bw40:00 raw:00 bw20:00 bw40:00 raw:00 bw20:00 bw40:00 raw:02 bw20:02 bw40:02 raw:00 bw20:00 bw40:00 Per channel power: tx_power ch1:09 ch2:09 tx_power ch3:0a ch4:0a tx_power ch5:0a ch6:0a tx_power ch7:0b ch8:0b tx_power ch9:0b ch10:0b tx_power ch11:0b ch12:0b tx_power ch13:0b ch14:0b
Reported-and-tested-by: Michael ZeroBeat@gmx.de Signed-off-by: Stanislaw Gruszka sgruszka@redhat.com Acked-by: Jakub Kicinski kubakici@wp.pl Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/mediatek/mt7601u/eeprom.h | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/net/wireless/mediatek/mt7601u/eeprom.h b/drivers/net/wireless/mediatek/mt7601u/eeprom.h index 662d12703b69..57b503ae63f1 100644 --- a/drivers/net/wireless/mediatek/mt7601u/eeprom.h +++ b/drivers/net/wireless/mediatek/mt7601u/eeprom.h @@ -17,7 +17,7 @@
struct mt7601u_dev;
-#define MT7601U_EE_MAX_VER 0x0c +#define MT7601U_EE_MAX_VER 0x0d #define MT7601U_EEPROM_SIZE 256
#define MT7601U_DEFAULT_TX_POWER 6
From: Russell King rmk+kernel@armlinux.org.uk
[ Upstream commit 5388a5b82199facacd3d7ac0d05aca6e8f902fed ]
machine_crash_nonpanic_core() does this:
while (1) cpu_relax();
because the kernel has crashed, and we have no known safe way to deal with the CPU. So, we place the CPU into an infinite loop which we expect it to never exit - at least not until the system as a whole is reset by some method.
In the absence of erratum 754327, this code assembles to:
b .
In other words, an infinite loop. When erratum 754327 is enabled, this becomes:
1: dmb b 1b
It has been observed that on some systems (eg, OMAP4) where, if a crash is triggered, the system tries to kexec into the panic kernel, but fails after taking the secondary CPU down - placing it into one of these loops. This causes the system to livelock, and the most noticable effect is the system stops after issuing:
Loading crashdump kernel...
to the system console.
The tested as working solution I came up with was to add wfe() to these infinite loops thusly:
while (1) { cpu_relax(); wfe(); }
which, without 754327 builds to:
1: wfe b 1b
or with 754327 is enabled:
1: dmb wfe b 1b
Adding "wfe" does two things depending on the environment we're running under: - where we're running on bare metal, and the processor implements "wfe", it stops us spinning endlessly in a loop where we're never going to do any useful work. - if we're running in a VM, it allows the CPU to be given back to the hypervisor and rescheduled for other purposes (maybe a different VM) rather than wasting CPU cycles inside a crashed VM.
However, in light of erratum 794072, Will Deacon wanted to see 10 nops as well - which is reasonable to cover the case where we have erratum 754327 enabled _and_ we have a processor that doesn't implement the wfe hint.
So, we now end up with:
1: wfe b 1b
when erratum 754327 is disabled, or:
1: dmb nop nop nop nop nop nop nop nop nop nop wfe b 1b
when erratum 754327 is enabled. We also get the dmb + 10 nop sequence elsewhere in the kernel, in terminating loops.
This is reasonable - it means we get the workaround for erratum 794072 when erratum 754327 is enabled, but still relinquish the dead processor - either by placing it in a lower power mode when wfe is implemented as such or by returning it to the hypervisior, or in the case where wfe is a no-op, we use the workaround specified in erratum 794072 to avoid the problem.
These as two entirely orthogonal problems - the 10 nops addresses erratum 794072, and the wfe is an optimisation that makes the system more efficient when crashed either in terms of power consumption or by allowing the host/other VMs to make use of the CPU.
I don't see any reason not to use kexec() inside a VM - it has the potential to provide automated recovery from a failure of the VMs kernel with the opportunity for saving a crashdump of the failure. A panic() with a reboot timeout won't do that, and reading the libvirt documentation, setting on_reboot to "preserve" won't either (the documentation states "The preserve action for an on_reboot event is treated as a destroy".) Surely it has to be a good thing to avoiding having CPUs spinning inside a VM that is doing no useful work.
Acked-by: Will Deacon will.deacon@arm.com Signed-off-by: Russell King rmk+kernel@armlinux.org.uk Signed-off-by: Sasha Levin sashal@kernel.org --- arch/arm/include/asm/barrier.h | 2 ++ arch/arm/include/asm/processor.h | 6 +++++- arch/arm/kernel/machine_kexec.c | 5 ++++- arch/arm/kernel/smp.c | 4 +++- arch/arm/mach-omap2/prm_common.c | 4 +++- 5 files changed, 17 insertions(+), 4 deletions(-)
diff --git a/arch/arm/include/asm/barrier.h b/arch/arm/include/asm/barrier.h index 513e03d138ea..8331cb0d3461 100644 --- a/arch/arm/include/asm/barrier.h +++ b/arch/arm/include/asm/barrier.h @@ -10,6 +10,8 @@ #define sev() __asm__ __volatile__ ("sev" : : : "memory") #define wfe() __asm__ __volatile__ ("wfe" : : : "memory") #define wfi() __asm__ __volatile__ ("wfi" : : : "memory") +#else +#define wfe() do { } while (0) #endif
#if __LINUX_ARM_ARCH__ >= 7 diff --git a/arch/arm/include/asm/processor.h b/arch/arm/include/asm/processor.h index 8a1e8e995dae..08509183c7df 100644 --- a/arch/arm/include/asm/processor.h +++ b/arch/arm/include/asm/processor.h @@ -77,7 +77,11 @@ extern void release_thread(struct task_struct *); unsigned long get_wchan(struct task_struct *p);
#if __LINUX_ARM_ARCH__ == 6 || defined(CONFIG_ARM_ERRATA_754327) -#define cpu_relax() smp_mb() +#define cpu_relax() \ + do { \ + smp_mb(); \ + __asm__ __volatile__("nop; nop; nop; nop; nop; nop; nop; nop; nop; nop;"); \ + } while (0) #else #define cpu_relax() barrier() #endif diff --git a/arch/arm/kernel/machine_kexec.c b/arch/arm/kernel/machine_kexec.c index b18c1ea56bed..ef6b27fe1d2e 100644 --- a/arch/arm/kernel/machine_kexec.c +++ b/arch/arm/kernel/machine_kexec.c @@ -87,8 +87,11 @@ void machine_crash_nonpanic_core(void *unused)
set_cpu_online(smp_processor_id(), false); atomic_dec(&waiting_for_crash_ipi); - while (1) + + while (1) { cpu_relax(); + wfe(); + } }
static void machine_kexec_mask_interrupts(void) diff --git a/arch/arm/kernel/smp.c b/arch/arm/kernel/smp.c index bc83ec7ed53f..7a5dc011c523 100644 --- a/arch/arm/kernel/smp.c +++ b/arch/arm/kernel/smp.c @@ -602,8 +602,10 @@ static void ipi_cpu_stop(unsigned int cpu) local_fiq_disable(); local_irq_disable();
- while (1) + while (1) { cpu_relax(); + wfe(); + } }
static DEFINE_PER_CPU(struct completion *, cpu_completion); diff --git a/arch/arm/mach-omap2/prm_common.c b/arch/arm/mach-omap2/prm_common.c index f1ca9479491b..9e14604b9642 100644 --- a/arch/arm/mach-omap2/prm_common.c +++ b/arch/arm/mach-omap2/prm_common.c @@ -533,8 +533,10 @@ void omap_prm_reset_system(void)
prm_ll_data->reset_system();
- while (1) + while (1) { cpu_relax(); + wfe(); + } }
/**
From: Manfred Schlaegl manfred.schlaegl@ginzinger.com
[ Upstream commit 7ab57b76ebf632bf2231ccabe26bea33868118c6 ]
We increase the default limit for buffer memory allocation by a factor of 10 to 640K to prevent data loss when using fast serial interfaces.
For example when using RS485 without flow-control at speeds of 1Mbit/s an upwards we've run into problems such as applications being too slow to read out this buffer (on embedded devices based on imx53 or imx6).
If you want to write transmitted data to a slow SD card and thus have realtime requirements, this limit can become a problem.
That shouldn't be the case and 640K buffers fix such problems for us.
This value is a maximum limit for allocation only. It has no effect on systems that currently run fine. When transmission is slow enough applications and hardware can keep up and increasing this limit doesn't change anything.
It only _allows_ to allocate more than 2*64K in cases we currently fail to allocate memory despite having some.
Signed-off-by: Manfred Schlaegl manfred.schlaegl@ginzinger.com Signed-off-by: Martin Kepplinger martin.kepplinger@ginzinger.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/tty/tty_buffer.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/tty/tty_buffer.c b/drivers/tty/tty_buffer.c index 41b9a7ccce08..ca9c82ee6c35 100644 --- a/drivers/tty/tty_buffer.c +++ b/drivers/tty/tty_buffer.c @@ -25,7 +25,7 @@ * Byte threshold to limit memory consumption for flip buffers. * The actual memory limit is > 2x this amount. */ -#define TTYB_DEFAULT_MEM_LIMIT 65536 +#define TTYB_DEFAULT_MEM_LIMIT (640 * 1024UL)
/* * We default to dicing tty buffer allocations to this many characters
From: Nathan Fontenot nfont@linux.vnet.ibm.com
[ Upstream commit 81b61324922c67f73813d8a9c175f3c153f6a1c6 ]
On pseries systems, performing a partition migration can result in altering the nodes a CPU is assigned to on the destination system. For exampl, pre-migration on the source system CPUs are in node 1 and 3, post-migration on the destination system CPUs are in nodes 2 and 3.
Handling the node change for a CPU can cause corruption in the slab cache if we hit a timing where a CPUs node is changed while cache_reap() is invoked. The corruption occurs because the slab cache code appears to rely on the CPU and slab cache pages being on the same node.
The current dynamic updating of a CPUs node done in arch/powerpc/mm/numa.c does not prevent us from hitting this scenario.
Changing the device tree property update notification handler that recognizes an affinity change for a CPU to do a full DLPAR remove and add of the CPU instead of dynamically changing its node resolves this issue.
Signed-off-by: Nathan Fontenot nfont@linux.vnet.ibm.com Signed-off-by: Michael W. Bringmann mwb@linux.vnet.ibm.com Tested-by: Michael W. Bringmann mwb@linux.vnet.ibm.com Signed-off-by: Michael Ellerman mpe@ellerman.id.au Signed-off-by: Sasha Levin sashal@kernel.org --- arch/powerpc/include/asm/topology.h | 2 ++ arch/powerpc/mm/numa.c | 9 +-------- arch/powerpc/platforms/pseries/hotplug-cpu.c | 19 +++++++++++++++++++ 3 files changed, 22 insertions(+), 8 deletions(-)
diff --git a/arch/powerpc/include/asm/topology.h b/arch/powerpc/include/asm/topology.h index 8b3b46b7b0f2..229c91bcf616 100644 --- a/arch/powerpc/include/asm/topology.h +++ b/arch/powerpc/include/asm/topology.h @@ -90,6 +90,8 @@ static inline int prrn_is_enabled(void) #define topology_sibling_cpumask(cpu) (per_cpu(cpu_sibling_map, cpu)) #define topology_core_cpumask(cpu) (per_cpu(cpu_core_map, cpu)) #define topology_core_id(cpu) (cpu_to_core_id(cpu)) + +int dlpar_cpu_readd(int cpu); #endif #endif
diff --git a/arch/powerpc/mm/numa.c b/arch/powerpc/mm/numa.c index 0ef83c274019..9cad2ed812ab 100644 --- a/arch/powerpc/mm/numa.c +++ b/arch/powerpc/mm/numa.c @@ -1540,13 +1540,6 @@ static void reset_topology_timer(void)
#ifdef CONFIG_SMP
-static void stage_topology_update(int core_id) -{ - cpumask_or(&cpu_associativity_changes_mask, - &cpu_associativity_changes_mask, cpu_sibling_mask(core_id)); - reset_topology_timer(); -} - static int dt_update_callback(struct notifier_block *nb, unsigned long action, void *data) { @@ -1559,7 +1552,7 @@ static int dt_update_callback(struct notifier_block *nb, !of_prop_cmp(update->prop->name, "ibm,associativity")) { u32 core_id; of_property_read_u32(update->dn, "reg", &core_id); - stage_topology_update(core_id); + rc = dlpar_cpu_readd(core_id); rc = NOTIFY_OK; } break; diff --git a/arch/powerpc/platforms/pseries/hotplug-cpu.c b/arch/powerpc/platforms/pseries/hotplug-cpu.c index a1b63e00b2f7..7a2beedb9740 100644 --- a/arch/powerpc/platforms/pseries/hotplug-cpu.c +++ b/arch/powerpc/platforms/pseries/hotplug-cpu.c @@ -785,6 +785,25 @@ static int dlpar_cpu_add_by_count(u32 cpus_to_add) return rc; }
+int dlpar_cpu_readd(int cpu) +{ + struct device_node *dn; + struct device *dev; + u32 drc_index; + int rc; + + dev = get_cpu_device(cpu); + dn = dev->of_node; + + rc = of_property_read_u32(dn, "ibm,my-drc-index", &drc_index); + + rc = dlpar_cpu_remove_by_index(drc_index); + if (!rc) + rc = dlpar_cpu_add(drc_index); + + return rc; +} + int dlpar_cpu(struct pseries_hp_errorlog *hp_elog) { u32 count, drc_index;
From: Akinobu Mita akinobu.mita@gmail.com
[ Upstream commit 29856308137de1c21eda89411695f4fc6e9780ff ]
This driver sets initial frame width and height to 0x0, which is invalid. So set it to selection rectangle bounds instead.
This is detected by v4l2-compliance detected.
Cc: Enrico Scholz enrico.scholz@sigma-chemnitz.de Cc: Michael Grzeschik m.grzeschik@pengutronix.de Cc: Marco Felsch m.felsch@pengutronix.de Signed-off-by: Akinobu Mita akinobu.mita@gmail.com Signed-off-by: Sakari Ailus sakari.ailus@linux.intel.com Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/i2c/mt9m111.c | 2 ++ 1 file changed, 2 insertions(+)
diff --git a/drivers/media/i2c/mt9m111.c b/drivers/media/i2c/mt9m111.c index 72e71b762827..a6145877bd00 100644 --- a/drivers/media/i2c/mt9m111.c +++ b/drivers/media/i2c/mt9m111.c @@ -974,6 +974,8 @@ static int mt9m111_probe(struct i2c_client *client, mt9m111->rect.top = MT9M111_MIN_DARK_ROWS; mt9m111->rect.width = MT9M111_MAX_WIDTH; mt9m111->rect.height = MT9M111_MAX_HEIGHT; + mt9m111->width = mt9m111->rect.width; + mt9m111->height = mt9m111->rect.height; mt9m111->fmt = &mt9m111_colour_fmts[0]; mt9m111->lastpage = -1; mutex_init(&mt9m111->power_lock);
From: David Tolnay dtolnay@gmail.com
[ Upstream commit aef027db48da56b6f25d0e54c07c8401ada6ce21 ]
The virtio-rng driver uses a completion called have_data to wait for a virtio read to be fulfilled by the hypervisor. The completion is reset before placing a buffer on the virtio queue and completed by the virtio callback once data has been written into the buffer.
Prior to this commit, the driver called init_completion on this completion both during probe as well as when registering virtio buffers as part of a hwrng read operation. The second of these init_completion calls should instead be reinit_completion because the have_data completion has already been inited by probe. As described in Documentation/scheduler/completion.txt, "Calling init_completion() twice on the same completion object is most likely a bug".
This bug was present in the initial implementation of virtio-rng in f7f510ec1957 ("virtio: An entropy device, as suggested by hpa"). Back then the have_data completion was a single static completion rather than a member of one of potentially multiple virtrng_info structs as implemented later by 08e53fbdb85c ("virtio-rng: support multiple virtio-rng devices"). The original driver incorrectly used init_completion rather than INIT_COMPLETION to reset have_data during read.
Tested by running `head -c48 /dev/random | hexdump` within crosvm, the Chrome OS virtual machine monitor, and confirming that the virtio-rng driver successfully produces random bytes from the host.
Signed-off-by: David Tolnay dtolnay@gmail.com Tested-by: David Tolnay dtolnay@gmail.com Signed-off-by: Herbert Xu herbert@gondor.apana.org.au Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/char/hw_random/virtio-rng.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/char/hw_random/virtio-rng.c b/drivers/char/hw_random/virtio-rng.c index 3fa2f8a009b3..1c5c4314c6b5 100644 --- a/drivers/char/hw_random/virtio-rng.c +++ b/drivers/char/hw_random/virtio-rng.c @@ -73,7 +73,7 @@ static int virtio_read(struct hwrng *rng, void *buf, size_t size, bool wait)
if (!vi->busy) { vi->busy = true; - init_completion(&vi->have_data); + reinit_completion(&vi->have_data); register_buffer(vi, buf, size); }
From: Timo Alho talho@nvidia.com
[ Upstream commit 51294bf6b9e897d595466dcda5a3f2751906a200 ]
On cases where device tree entries for fuse and clock provider are in different order, fuse driver needs to defer probing. This leads to freeing incorrect IO base address as the fuse->base variable gets overwritten once during first probe invocation. This leads to the following spew during boot:
[ 3.082285] Trying to vfree() nonexistent vm area (00000000cfe8fd94) [ 3.082308] WARNING: CPU: 5 PID: 126 at /hdd/l4t/kernel/stable/mm/vmalloc.c:1511 __vunmap+0xcc/0xd8 [ 3.082318] Modules linked in: [ 3.082330] CPU: 5 PID: 126 Comm: kworker/5:1 Tainted: G S 4.19.7-tegra-gce119d3 #1 [ 3.082340] Hardware name: quill (DT) [ 3.082353] Workqueue: events deferred_probe_work_func [ 3.082364] pstate: 40000005 (nZcv daif -PAN -UAO) [ 3.082372] pc : __vunmap+0xcc/0xd8 [ 3.082379] lr : __vunmap+0xcc/0xd8 [ 3.082385] sp : ffff00000a1d3b60 [ 3.082391] x29: ffff00000a1d3b60 x28: 0000000000000000 [ 3.082402] x27: 0000000000000000 x26: ffff000008e8b610 [ 3.082413] x25: 0000000000000000 x24: 0000000000000009 [ 3.082423] x23: ffff000009221a90 x22: ffff000009f6d000 [ 3.082432] x21: 0000000000000000 x20: 0000000000000000 [ 3.082442] x19: ffff000009f6d000 x18: ffffffffffffffff [ 3.082452] x17: 0000000000000000 x16: 0000000000000000 [ 3.082462] x15: ffff0000091396c8 x14: 0720072007200720 [ 3.082471] x13: 0720072007200720 x12: 0720072907340739 [ 3.082481] x11: 0764076607380765 x10: 0766076307300730 [ 3.082491] x9 : 0730073007300730 x8 : 0730073007280720 [ 3.082501] x7 : 0761076507720761 x6 : 0000000000000102 [ 3.082510] x5 : 0000000000000000 x4 : 0000000000000000 [ 3.082519] x3 : ffffffffffffffff x2 : ffff000009150ff8 [ 3.082528] x1 : 3d95b1429fff5200 x0 : 0000000000000000 [ 3.082538] Call trace: [ 3.082545] __vunmap+0xcc/0xd8 [ 3.082552] vunmap+0x24/0x30 [ 3.082561] __iounmap+0x2c/0x38 [ 3.082569] tegra_fuse_probe+0xc8/0x118 [ 3.082577] platform_drv_probe+0x50/0xa0 [ 3.082585] really_probe+0x1b0/0x288 [ 3.082593] driver_probe_device+0x58/0x100 [ 3.082601] __device_attach_driver+0x98/0xf0 [ 3.082609] bus_for_each_drv+0x64/0xc8 [ 3.082616] __device_attach+0xd8/0x130 [ 3.082624] device_initial_probe+0x10/0x18 [ 3.082631] bus_probe_device+0x90/0x98 [ 3.082638] deferred_probe_work_func+0x74/0xb0 [ 3.082649] process_one_work+0x1e0/0x318 [ 3.082656] worker_thread+0x228/0x450 [ 3.082664] kthread+0x128/0x130 [ 3.082672] ret_from_fork+0x10/0x18 [ 3.082678] ---[ end trace 0810fe6ba772c1c7 ]---
Fix this by retaining the value of fuse->base until driver has successfully probed.
Signed-off-by: Timo Alho talho@nvidia.com Acked-by: Jon Hunter jonathanh@nvidia.com Signed-off-by: Thierry Reding treding@nvidia.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/soc/tegra/fuse/fuse-tegra.c | 12 +++++++++--- 1 file changed, 9 insertions(+), 3 deletions(-)
diff --git a/drivers/soc/tegra/fuse/fuse-tegra.c b/drivers/soc/tegra/fuse/fuse-tegra.c index de2c1bfe28b5..c4f5e5bbb8dc 100644 --- a/drivers/soc/tegra/fuse/fuse-tegra.c +++ b/drivers/soc/tegra/fuse/fuse-tegra.c @@ -131,13 +131,17 @@ static int tegra_fuse_probe(struct platform_device *pdev) /* take over the memory region from the early initialization */ res = platform_get_resource(pdev, IORESOURCE_MEM, 0); fuse->base = devm_ioremap_resource(&pdev->dev, res); - if (IS_ERR(fuse->base)) - return PTR_ERR(fuse->base); + if (IS_ERR(fuse->base)) { + err = PTR_ERR(fuse->base); + fuse->base = base; + return err; + }
fuse->clk = devm_clk_get(&pdev->dev, "fuse"); if (IS_ERR(fuse->clk)) { dev_err(&pdev->dev, "failed to get FUSE clock: %ld", PTR_ERR(fuse->clk)); + fuse->base = base; return PTR_ERR(fuse->clk); }
@@ -146,8 +150,10 @@ static int tegra_fuse_probe(struct platform_device *pdev)
if (fuse->soc->probe) { err = fuse->soc->probe(fuse); - if (err < 0) + if (err < 0) { + fuse->base = base; return err; + } }
if (tegra_fuse_create_sysfs(&pdev->dev, fuse->soc->info->size,
From: Song Hongyan hongyan.song@intel.com
[ Upstream commit 2edefc056e4f0e6ec9508dd1aca2c18fa320efef ]
Host driver should handle interrupt mask register earlier than wake up ish FW else there will be conditions when FW interrupt comes, host PIMR register still not set ready, so move the interrupt mask setting before ish_wakeup.
Clear PISR busy_clear bit in ish_irq_handler. If not clear, there will be conditions host driver received a busy_clear interrupt (before the busy_clear mask bit is ready), it will return IRQ_NONE after check_generated_interrupt, the interrupt will never be cleared, causing the DEVICE not sending following IRQ.
Since PISR clear should not be called for the CHV device we do this change. After the change, both ISH2HOST interrupt and busy_clear interrupt will be considered as interrupt from ISH, busy_clear interrupt will return IRQ_HANDLED from IPC_IS_BUSY check.
Signed-off-by: Song Hongyan hongyan.song@intel.com Acked-by: Srinivas Pandruvada srinivas.pandruvada@linux.intel.com Signed-off-by: Jiri Kosina jkosina@suse.cz Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/hid/intel-ish-hid/ipc/ipc.c | 9 ++++++--- 1 file changed, 6 insertions(+), 3 deletions(-)
diff --git a/drivers/hid/intel-ish-hid/ipc/ipc.c b/drivers/hid/intel-ish-hid/ipc/ipc.c index 0c9ac4d5d850..41d44536aa15 100644 --- a/drivers/hid/intel-ish-hid/ipc/ipc.c +++ b/drivers/hid/intel-ish-hid/ipc/ipc.c @@ -92,7 +92,10 @@ static bool check_generated_interrupt(struct ishtp_device *dev) IPC_INT_FROM_ISH_TO_HOST_CHV_AB(pisr_val); } else { pisr_val = ish_reg_read(dev, IPC_REG_PISR_BXT); - interrupt_generated = IPC_INT_FROM_ISH_TO_HOST_BXT(pisr_val); + interrupt_generated = !!pisr_val; + /* only busy-clear bit is RW, others are RO */ + if (pisr_val) + ish_reg_write(dev, IPC_REG_PISR_BXT, pisr_val); }
return interrupt_generated; @@ -795,11 +798,11 @@ int ish_hw_start(struct ishtp_device *dev) { ish_set_host_rdy(dev);
+ set_host_ready(dev); + /* After that we can enable ISH DMA operation and wakeup ISHFW */ ish_wakeup(dev);
- set_host_ready(dev); - /* wait for FW-initiated reset flow */ if (!dev->recvd_hw_ready) wait_event_interruptible_timeout(dev->wait_hw_ready,
From: Marcel Holtmann marcel@holtmann.org
[ Upstream commit 7c9cbd0b5e38a1672fcd137894ace3b042dfbf69 ]
The function l2cap_get_conf_opt will return L2CAP_CONF_OPT_SIZE + opt->len as length value. The opt->len however is in control over the remote user and can be used by an attacker to gain access beyond the bounds of the actual packet.
To prevent any potential leak of heap memory, it is enough to check that the resulting len calculation after calling l2cap_get_conf_opt is not below zero. A well formed packet will always return >= 0 here and will end with the length value being zero after the last option has been parsed. In case of malformed packets messing with the opt->len field the length value will become negative. If that is the case, then just abort and ignore the option.
In case an attacker uses a too short opt->len value, then garbage will be parsed, but that is protected by the unknown option handling and also the option parameter size checks.
Signed-off-by: Marcel Holtmann marcel@holtmann.org Reviewed-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Johan Hedberg johan.hedberg@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- net/bluetooth/l2cap_core.c | 6 ++++++ 1 file changed, 6 insertions(+)
diff --git a/net/bluetooth/l2cap_core.c b/net/bluetooth/l2cap_core.c index 1fc23cb4a3e0..bf7a2846a85f 100644 --- a/net/bluetooth/l2cap_core.c +++ b/net/bluetooth/l2cap_core.c @@ -3326,6 +3326,8 @@ static int l2cap_parse_conf_req(struct l2cap_chan *chan, void *data, size_t data
while (len >= L2CAP_CONF_OPT_SIZE) { len -= l2cap_get_conf_opt(&req, &type, &olen, &val); + if (len < 0) + break;
hint = type & L2CAP_CONF_HINT; type &= L2CAP_CONF_MASK; @@ -3537,6 +3539,8 @@ static int l2cap_parse_conf_rsp(struct l2cap_chan *chan, void *rsp, int len,
while (len >= L2CAP_CONF_OPT_SIZE) { len -= l2cap_get_conf_opt(&rsp, &type, &olen, &val); + if (len < 0) + break;
switch (type) { case L2CAP_CONF_MTU: @@ -3717,6 +3721,8 @@ static void l2cap_conf_rfc_get(struct l2cap_chan *chan, void *rsp, int len)
while (len >= L2CAP_CONF_OPT_SIZE) { len -= l2cap_get_conf_opt(&rsp, &type, &olen, &val); + if (len < 0) + break;
switch (type) { case L2CAP_CONF_RFC:
From: Buland Singh bsingh@redhat.com
[ Upstream commit 24d48a61f2666630da130cc2ec2e526eacf229e3 ]
Commit '3d035f580699 ("drivers/char/hpet.c: allow user controlled mmap for user processes")' introduced a new kernel command line parameter hpet_mmap, that is required to expose the memory map of the HPET registers to user-space. Unfortunately the kernel command line parameter 'hpet_mmap' is broken and never takes effect due to missing '=' character in the __setup() code of hpet_mmap_enable.
Before this patch:
dmesg output with the kernel command line parameter hpet_mmap=1
[ 0.204152] HPET mmap disabled
dmesg output with the kernel command line parameter hpet_mmap=0
[ 0.204192] HPET mmap disabled
After this patch:
dmesg output with the kernel command line parameter hpet_mmap=1
[ 0.203945] HPET mmap enabled
dmesg output with the kernel command line parameter hpet_mmap=0
[ 0.204652] HPET mmap disabled
Fixes: 3d035f580699 ("drivers/char/hpet.c: allow user controlled mmap for user processes") Signed-off-by: Buland Singh bsingh@redhat.com Signed-off-by: Greg Kroah-Hartman gregkh@linuxfoundation.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/char/hpet.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/char/hpet.c b/drivers/char/hpet.c index 50272fe81f26..818a8d40e5c9 100644 --- a/drivers/char/hpet.c +++ b/drivers/char/hpet.c @@ -376,7 +376,7 @@ static __init int hpet_mmap_enable(char *str) pr_info("HPET mmap %s\n", hpet_mmap_enabled ? "enabled" : "disabled"); return 1; } -__setup("hpet_mmap", hpet_mmap_enable); +__setup("hpet_mmap=", hpet_mmap_enable);
static int hpet_mmap(struct file *file, struct vm_area_struct *vma) {
From: Anders Roxell anders.roxell@linaro.org
[ Upstream commit 9227ab5643cb8350449502dd9e3168a873ab0e3b ]
The warning got introduced by commit 930507c18304 ("arm64: add basic Kconfig symbols for i.MX8"). Since it got enabled for arm64. The warning haven't been seen before since size_t was 'unsigned int' when built on arm32.
../drivers/dma/imx-dma.c: In function ‘imxdma_sg_next’: ../include/linux/kernel.h:846:29: warning: comparison of distinct pointer types lacks a cast (!!(sizeof((typeof(x) *)1 == (typeof(y) *)1))) ^~ ../include/linux/kernel.h:860:4: note: in expansion of macro ‘__typecheck’ (__typecheck(x, y) && __no_side_effects(x, y)) ^~~~~~~~~~~ ../include/linux/kernel.h:870:24: note: in expansion of macro ‘__safe_cmp’ __builtin_choose_expr(__safe_cmp(x, y), \ ^~~~~~~~~~ ../include/linux/kernel.h:879:19: note: in expansion of macro ‘__careful_cmp’ #define min(x, y) __careful_cmp(x, y, <) ^~~~~~~~~~~~~ ../drivers/dma/imx-dma.c:288:8: note: in expansion of macro ‘min’ now = min(d->len, sg_dma_len(sg)); ^~~
Rework so that we use min_t and pass in the size_t that returns the minimum of two values, using the specified type.
Signed-off-by: Anders Roxell anders.roxell@linaro.org Acked-by: Olof Johansson olof@lixom.net Reviewed-by: Fabio Estevam festevam@gmail.com Signed-off-by: Vinod Koul vkoul@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/dma/imx-dma.c | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/drivers/dma/imx-dma.c b/drivers/dma/imx-dma.c index 1cfa1d9bc971..f8786f60cdc1 100644 --- a/drivers/dma/imx-dma.c +++ b/drivers/dma/imx-dma.c @@ -290,7 +290,7 @@ static inline int imxdma_sg_next(struct imxdma_desc *d) struct scatterlist *sg = d->sg; unsigned long now;
- now = min(d->len, sg_dma_len(sg)); + now = min_t(size_t, d->len, sg_dma_len(sg)); if (d->len != IMX_DMA_LENGTH_LOOP) d->len -= now;
From: Shunyong Yang shunyong.yang@hxt-semitech.com
[ Upstream commit 546c0547555efca8ba8c120716c325435e29df1b ]
When dma_cookie_complete() is called in hidma_process_completed(), dma_cookie_status() will return DMA_COMPLETE in hidma_tx_status(). Then, hidma_txn_is_success() will be called to use channel cookie mchan->last_success to do additional DMA status check. Current code assigns mchan->last_success after dma_cookie_complete(). This causes a race condition of dma_cookie_status() returns DMA_COMPLETE before mchan->last_success is assigned correctly. The race will cause hidma_tx_status() return DMA_ERROR but the transaction is actually a success. Moreover, in async_tx case, it will cause a timeout panic in async_tx_quiesce().
Kernel panic - not syncing: async_tx_quiesce: DMA error waiting for transaction ... Call trace: [<ffff000008089994>] dump_backtrace+0x0/0x1f4 [<ffff000008089bac>] show_stack+0x24/0x2c [<ffff00000891e198>] dump_stack+0x84/0xa8 [<ffff0000080da544>] panic+0x12c/0x29c [<ffff0000045d0334>] async_tx_quiesce+0xa4/0xc8 [async_tx] [<ffff0000045d03c8>] async_trigger_callback+0x70/0x1c0 [async_tx] [<ffff0000048b7d74>] raid_run_ops+0x86c/0x1540 [raid456] [<ffff0000048bd084>] handle_stripe+0x5e8/0x1c7c [raid456] [<ffff0000048be9ec>] handle_active_stripes.isra.45+0x2d4/0x550 [raid456] [<ffff0000048beff4>] raid5d+0x38c/0x5d0 [raid456] [<ffff000008736538>] md_thread+0x108/0x168 [<ffff0000080fb1cc>] kthread+0x10c/0x138 [<ffff000008084d34>] ret_from_fork+0x10/0x18
Cc: Joey Zheng yu.zheng@hxt-semitech.com Reviewed-by: Sinan Kaya okaya@kernel.org Signed-off-by: Shunyong Yang shunyong.yang@hxt-semitech.com Signed-off-by: Vinod Koul vkoul@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/dma/qcom/hidma.c | 17 +++++++++-------- 1 file changed, 9 insertions(+), 8 deletions(-)
diff --git a/drivers/dma/qcom/hidma.c b/drivers/dma/qcom/hidma.c index e244e10a94b5..5444f39bf939 100644 --- a/drivers/dma/qcom/hidma.c +++ b/drivers/dma/qcom/hidma.c @@ -131,24 +131,25 @@ static void hidma_process_completed(struct hidma_chan *mchan) desc = &mdesc->desc; last_cookie = desc->cookie;
+ llstat = hidma_ll_status(mdma->lldev, mdesc->tre_ch); + spin_lock_irqsave(&mchan->lock, irqflags); + if (llstat == DMA_COMPLETE) { + mchan->last_success = last_cookie; + result.result = DMA_TRANS_NOERROR; + } else { + result.result = DMA_TRANS_ABORTED; + } + dma_cookie_complete(desc); spin_unlock_irqrestore(&mchan->lock, irqflags);
- llstat = hidma_ll_status(mdma->lldev, mdesc->tre_ch); dmaengine_desc_get_callback(desc, &cb);
dma_run_dependencies(desc);
spin_lock_irqsave(&mchan->lock, irqflags); list_move(&mdesc->node, &mchan->free); - - if (llstat == DMA_COMPLETE) { - mchan->last_success = last_cookie; - result.result = DMA_TRANS_NOERROR; - } else - result.result = DMA_TRANS_ABORTED; - spin_unlock_irqrestore(&mchan->lock, irqflags);
dmaengine_desc_callback_invoke(&cb, &result);
From: Florian Westphal fw@strlen.de
[ Upstream commit 8e2f311a68494a6677c1724bdcb10bada21af37c ]
Following command: iptables -D FORWARD -m physdev ... causes connectivity loss in some setups.
Reason is that iptables userspace will probe kernel for the module revision of the physdev patch, and physdev has an artificial dependency on br_netfilter (xt_physdev use makes no sense unless a br_netfilter module is loaded).
This causes the "phydev" module to be loaded, which in turn enables the "call-iptables" infrastructure.
bridged packets might then get dropped by the iptables ruleset.
The better fix would be to change the "call-iptables" defaults to 0 and enforce explicit setting to 1, but that breaks backwards compatibility.
This does the next best thing: add a request_module call to checkentry. This was a stray '-D ... -m physdev' won't activate br_netfilter anymore.
Signed-off-by: Florian Westphal fw@strlen.de Signed-off-by: Pablo Neira Ayuso pablo@netfilter.org Signed-off-by: Sasha Levin sashal@kernel.org --- include/net/netfilter/br_netfilter.h | 1 - net/bridge/br_netfilter_hooks.c | 5 ----- net/netfilter/xt_physdev.c | 9 +++++++-- 3 files changed, 7 insertions(+), 8 deletions(-)
diff --git a/include/net/netfilter/br_netfilter.h b/include/net/netfilter/br_netfilter.h index 0b0c35c37125..238d1b83a45a 100644 --- a/include/net/netfilter/br_netfilter.h +++ b/include/net/netfilter/br_netfilter.h @@ -48,7 +48,6 @@ static inline struct rtable *bridge_parent_rtable(const struct net_device *dev) }
struct net_device *setup_pre_routing(struct sk_buff *skb); -void br_netfilter_enable(void);
#if IS_ENABLED(CONFIG_IPV6) int br_validate_ipv6(struct net *net, struct sk_buff *skb); diff --git a/net/bridge/br_netfilter_hooks.c b/net/bridge/br_netfilter_hooks.c index 7e42c0d1f55b..38865deab3ac 100644 --- a/net/bridge/br_netfilter_hooks.c +++ b/net/bridge/br_netfilter_hooks.c @@ -878,11 +878,6 @@ static const struct nf_br_ops br_ops = { .br_dev_xmit_hook = br_nf_dev_xmit, };
-void br_netfilter_enable(void) -{ -} -EXPORT_SYMBOL_GPL(br_netfilter_enable); - /* For br_nf_post_routing, we need (prio = NF_BR_PRI_LAST), because * br_dev_queue_push_xmit is called afterwards */ static struct nf_hook_ops br_nf_ops[] __read_mostly = { diff --git a/net/netfilter/xt_physdev.c b/net/netfilter/xt_physdev.c index bb33598e4530..ec247d8370e8 100644 --- a/net/netfilter/xt_physdev.c +++ b/net/netfilter/xt_physdev.c @@ -96,8 +96,7 @@ physdev_mt(const struct sk_buff *skb, struct xt_action_param *par) static int physdev_mt_check(const struct xt_mtchk_param *par) { const struct xt_physdev_info *info = par->matchinfo; - - br_netfilter_enable(); + static bool brnf_probed __read_mostly;
if (!(info->bitmask & XT_PHYSDEV_OP_MASK) || info->bitmask & ~XT_PHYSDEV_OP_MASK) @@ -113,6 +112,12 @@ static int physdev_mt_check(const struct xt_mtchk_param *par) if (par->hook_mask & (1 << NF_INET_LOCAL_OUT)) return -EINVAL; } + + if (!brnf_probed) { + brnf_probed = true; + request_module("br_netfilter"); + } + return 0; }
From: Pawe? Chmiel pawel.mikolaj.chmiel@gmail.com
[ Upstream commit 49710c32cd9d6626a77c9f5f978a5f58cb536b35 ]
Previously when doing format enumeration, it was returning all formats supported by driver, even if they're not supported by hw. Add missing check for fmt_ver_flag, so it'll be fixed and only those supported by hw will be returned. Similar thing is already done in s5p_jpeg_find_format.
It was found by using v4l2-compliance tool and checking result of VIDIOC_ENUM_FMT/FRAMESIZES/FRAMEINTERVALS test and using v4l2-ctl to get list of all supported formats.
Tested on s5pv210-galaxys (Samsung i9000 phone).
Fixes: bb677f3ac434 ("[media] Exynos4 JPEG codec v4l2 driver")
Signed-off-by: Pawe? Chmiel pawel.mikolaj.chmiel@gmail.com Reviewed-by: Jacek Anaszewski jacek.anaszewski@gmail.com [hverkuil-cisco@xs4all.nl: fix a few alignment issues] Signed-off-by: Mauro Carvalho Chehab mchehab+samsung@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/media/platform/s5p-jpeg/jpeg-core.c | 19 +++++++++++-------- 1 file changed, 11 insertions(+), 8 deletions(-)
diff --git a/drivers/media/platform/s5p-jpeg/jpeg-core.c b/drivers/media/platform/s5p-jpeg/jpeg-core.c index 06e2b72d07ca..c89922fb42ce 100644 --- a/drivers/media/platform/s5p-jpeg/jpeg-core.c +++ b/drivers/media/platform/s5p-jpeg/jpeg-core.c @@ -1264,13 +1264,16 @@ static int s5p_jpeg_querycap(struct file *file, void *priv, return 0; }
-static int enum_fmt(struct s5p_jpeg_fmt *sjpeg_formats, int n, +static int enum_fmt(struct s5p_jpeg_ctx *ctx, + struct s5p_jpeg_fmt *sjpeg_formats, int n, struct v4l2_fmtdesc *f, u32 type) { int i, num = 0; + unsigned int fmt_ver_flag = ctx->jpeg->variant->fmt_ver_flag;
for (i = 0; i < n; ++i) { - if (sjpeg_formats[i].flags & type) { + if (sjpeg_formats[i].flags & type && + sjpeg_formats[i].flags & fmt_ver_flag) { /* index-th format of type type found ? */ if (num == f->index) break; @@ -1297,11 +1300,11 @@ static int s5p_jpeg_enum_fmt_vid_cap(struct file *file, void *priv, struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
if (ctx->mode == S5P_JPEG_ENCODE) - return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f, + return enum_fmt(ctx, sjpeg_formats, SJPEG_NUM_FORMATS, f, SJPEG_FMT_FLAG_ENC_CAPTURE);
- return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f, - SJPEG_FMT_FLAG_DEC_CAPTURE); + return enum_fmt(ctx, sjpeg_formats, SJPEG_NUM_FORMATS, f, + SJPEG_FMT_FLAG_DEC_CAPTURE); }
static int s5p_jpeg_enum_fmt_vid_out(struct file *file, void *priv, @@ -1310,11 +1313,11 @@ static int s5p_jpeg_enum_fmt_vid_out(struct file *file, void *priv, struct s5p_jpeg_ctx *ctx = fh_to_ctx(priv);
if (ctx->mode == S5P_JPEG_ENCODE) - return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f, + return enum_fmt(ctx, sjpeg_formats, SJPEG_NUM_FORMATS, f, SJPEG_FMT_FLAG_ENC_OUTPUT);
- return enum_fmt(sjpeg_formats, SJPEG_NUM_FORMATS, f, - SJPEG_FMT_FLAG_DEC_OUTPUT); + return enum_fmt(ctx, sjpeg_formats, SJPEG_NUM_FORMATS, f, + SJPEG_FMT_FLAG_DEC_OUTPUT); }
static struct s5p_jpeg_q_data *get_q_data(struct s5p_jpeg_ctx *ctx,
From: Axel Lin axel.lin@ingics.com
[ Upstream commit f01a7beb6791f1c419424c1a6958b7d0a289c974 ]
The act8600_sudcdc_voltage_ranges setting does not match the datasheet.
The problems in below entry: REGULATOR_LINEAR_RANGE(19000000, 191, 255, 400000),
1. The off-by-one min_sel causes wrong volatage calculation. The min_sel should be 192. 2. According to the datasheet[1] Table 7. (on page 43): The selector 248 (0b11111000) ~ 255 (0b11111111) are 41.400V.
Also fix off-by-one for ACT8600_SUDCDC_VOLTAGE_NUM.
[1] https://active-semi.com/wp-content/uploads/ACT8600_Datasheet.pdf
Fixes: df3a950e4e73 ("regulator: act8865: Add act8600 support") Signed-off-by: Axel Lin axel.lin@ingics.com Signed-off-by: Mark Brown broonie@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/regulator/act8865-regulator.c | 5 +++-- 1 file changed, 3 insertions(+), 2 deletions(-)
diff --git a/drivers/regulator/act8865-regulator.c b/drivers/regulator/act8865-regulator.c index 7652477e6a9d..39e8d60df060 100644 --- a/drivers/regulator/act8865-regulator.c +++ b/drivers/regulator/act8865-regulator.c @@ -131,7 +131,7 @@ * ACT8865 voltage number */ #define ACT8865_VOLTAGE_NUM 64 -#define ACT8600_SUDCDC_VOLTAGE_NUM 255 +#define ACT8600_SUDCDC_VOLTAGE_NUM 256
struct act8865 { struct regmap *regmap; @@ -222,7 +222,8 @@ static const struct regulator_linear_range act8600_sudcdc_voltage_ranges[] = { REGULATOR_LINEAR_RANGE(3000000, 0, 63, 0), REGULATOR_LINEAR_RANGE(3000000, 64, 159, 100000), REGULATOR_LINEAR_RANGE(12600000, 160, 191, 200000), - REGULATOR_LINEAR_RANGE(19000000, 191, 255, 400000), + REGULATOR_LINEAR_RANGE(19000000, 192, 247, 400000), + REGULATOR_LINEAR_RANGE(41400000, 248, 255, 0), };
static struct regulator_ops act8865_ops = {
From: Daniel Vetter daniel.vetter@ffwll.ch
[ Upstream commit 934c5b32a5e43d8de2ab4f1566f91d7c3bf8cb64 ]
The correct way for legacy drivers to update properties that need to do a full modeset, is to do a full modeset.
Note that we don't need to call the drm_mode_config_internal helper because we're not changing any of the refcounted paramters.
v2: Fixup error handling (Ville). Since the old code didn't bother I decided to just delete it instead of adding even more code for just error handling.
Cc: Ville Syrjälä ville.syrjala@linux.intel.com Reviewed-by: Alex Deucher alexander.deucher@amd.com (v1) Cc: Sean Paul seanpaul@chromium.org Signed-off-by: Daniel Vetter daniel.vetter@intel.com Link: https://patchwork.freedesktop.org/patch/msgid/20181217194303.14397-2-daniel.... Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpu/drm/nouveau/dispnv04/tvnv17.c | 4 +++- 1 file changed, 3 insertions(+), 1 deletion(-)
diff --git a/drivers/gpu/drm/nouveau/dispnv04/tvnv17.c b/drivers/gpu/drm/nouveau/dispnv04/tvnv17.c index 434d1e29f279..cd37d00e9723 100644 --- a/drivers/gpu/drm/nouveau/dispnv04/tvnv17.c +++ b/drivers/gpu/drm/nouveau/dispnv04/tvnv17.c @@ -750,7 +750,9 @@ static int nv17_tv_set_property(struct drm_encoder *encoder, /* Disable the crtc to ensure a full modeset is * performed whenever it's turned on again. */ if (crtc) - drm_crtc_force_disable(crtc); + drm_crtc_helper_set_mode(crtc, &crtc->mode, + crtc->x, crtc->y, + crtc->primary->fb); }
return 0;
From: George Rimar grimar@accesssoftek.com
[ Upstream commit 927185c124d62a9a4d35878d7f6d432a166b74e3 ]
The kernel uses the OUTPUT_FORMAT linker script command in it's linker scripts. Most of the time, the -m option is passed to the linker with correct architecture, but sometimes (at least for x86_64) the -m option contradicts the OUTPUT_FORMAT directive.
Specifically, arch/x86/boot and arch/x86/realmode/rm produce i386 object files, but are linked with the -m elf_x86_64 linker flag when building for x86_64.
The GNU linker manpage doesn't explicitly state any tie-breakers between -m and OUTPUT_FORMAT. But with BFD and Gold linkers, OUTPUT_FORMAT overrides the emulation value specified with the -m option.
LLVM lld has a different behavior, however. When supplied with contradicting -m and OUTPUT_FORMAT values it fails with the following error message:
ld.lld: error: arch/x86/realmode/rm/header.o is incompatible with elf_x86_64
Therefore, just add the correct -m after the incorrect one (it overrides it), so the linker invocation looks like this:
ld -m elf_x86_64 -z max-page-size=0x200000 -m elf_i386 --emit-relocs -T \ realmode.lds header.o trampoline_64.o stack.o reboot.o -o realmode.elf
This is not a functional change for GNU ld, because (although not explicitly documented) OUTPUT_FORMAT overrides -m EMULATION.
Tested by building x86_64 kernel with GNU gcc/ld toolchain and booting it in QEMU.
[ bp: massage and clarify text. ]
Suggested-by: Dmitry Golovin dima@golovin.in Signed-off-by: George Rimar grimar@accesssoftek.com Signed-off-by: Tri Vo trong@android.com Signed-off-by: Borislav Petkov bp@suse.de Tested-by: Tri Vo trong@android.com Tested-by: Nick Desaulniers ndesaulniers@google.com Cc: "H. Peter Anvin" hpa@zytor.com Cc: Ingo Molnar mingo@redhat.com Cc: Michael Matz matz@suse.de Cc: Thomas Gleixner tglx@linutronix.de Cc: morbo@google.com Cc: ndesaulniers@google.com Cc: ruiu@google.com Cc: x86-ml x86@kernel.org Link: https://lkml.kernel.org/r/20190111201012.71210-1-trong@android.com Signed-off-by: Sasha Levin sashal@kernel.org --- arch/x86/boot/Makefile | 2 +- arch/x86/realmode/rm/Makefile | 2 +- 2 files changed, 2 insertions(+), 2 deletions(-)
diff --git a/arch/x86/boot/Makefile b/arch/x86/boot/Makefile index 3b7156f46bc1..3b16935b22bc 100644 --- a/arch/x86/boot/Makefile +++ b/arch/x86/boot/Makefile @@ -100,7 +100,7 @@ $(obj)/zoffset.h: $(obj)/compressed/vmlinux FORCE AFLAGS_header.o += -I$(objtree)/$(obj) $(obj)/header.o: $(obj)/zoffset.h
-LDFLAGS_setup.elf := -T +LDFLAGS_setup.elf := -m elf_i386 -T $(obj)/setup.elf: $(src)/setup.ld $(SETUP_OBJS) FORCE $(call if_changed,ld)
diff --git a/arch/x86/realmode/rm/Makefile b/arch/x86/realmode/rm/Makefile index 25012abc3409..ce5f431e6823 100644 --- a/arch/x86/realmode/rm/Makefile +++ b/arch/x86/realmode/rm/Makefile @@ -47,7 +47,7 @@ $(obj)/pasyms.h: $(REALMODE_OBJS) FORCE targets += realmode.lds $(obj)/realmode.lds: $(obj)/pasyms.h
-LDFLAGS_realmode.elf := --emit-relocs -T +LDFLAGS_realmode.elf := -m elf_i386 --emit-relocs -T CPPFLAGS_realmode.lds += -P -C -I$(objtree)/$(obj)
targets += realmode.elf
From: Ondrej Mosnacek omosnace@redhat.com
[ Upstream commit 53e0c2aa9a59a48e3798ef193d573ade85aa80f5 ]
Ignore all selinux_inode_notifysecctx() calls on mounts with SBLABEL_MNT flag unset. This is achived by returning -EOPNOTSUPP for this case in selinux_inode_setsecurtity() (because that function should not be called in such case anyway) and translating this error to 0 in selinux_inode_notifysecctx().
This fixes behavior of kernfs-based filesystems when mounted with the 'context=' option. Before this patch, if a node's context had been explicitly set to a non-default value and later the filesystem has been remounted with the 'context=' option, then this node would show up as having the manually-set context and not the mount-specified one.
Steps to reproduce: # mount -t cgroup2 cgroup2 /sys/fs/cgroup/unified # chcon unconfined_u:object_r:user_home_t:s0 /sys/fs/cgroup/unified/cgroup.stat # ls -lZ /sys/fs/cgroup/unified total 0 -r--r--r--. 1 root root system_u:object_r:cgroup_t:s0 0 Dec 13 10:41 cgroup.controllers -rw-r--r--. 1 root root system_u:object_r:cgroup_t:s0 0 Dec 13 10:41 cgroup.max.depth -rw-r--r--. 1 root root system_u:object_r:cgroup_t:s0 0 Dec 13 10:41 cgroup.max.descendants -rw-r--r--. 1 root root system_u:object_r:cgroup_t:s0 0 Dec 13 10:41 cgroup.procs -r--r--r--. 1 root root unconfined_u:object_r:user_home_t:s0 0 Dec 13 10:41 cgroup.stat -rw-r--r--. 1 root root system_u:object_r:cgroup_t:s0 0 Dec 13 10:41 cgroup.subtree_control -rw-r--r--. 1 root root system_u:object_r:cgroup_t:s0 0 Dec 13 10:41 cgroup.threads # umount /sys/fs/cgroup/unified # mount -o context=system_u:object_r:tmpfs_t:s0 -t cgroup2 cgroup2 /sys/fs/cgroup/unified
Result before: # ls -lZ /sys/fs/cgroup/unified total 0 -r--r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.controllers -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.max.depth -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.max.descendants -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.procs -r--r--r--. 1 root root unconfined_u:object_r:user_home_t:s0 0 Dec 13 10:41 cgroup.stat -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.subtree_control -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.threads
Result after: # ls -lZ /sys/fs/cgroup/unified total 0 -r--r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.controllers -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.max.depth -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.max.descendants -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.procs -r--r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.stat -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.subtree_control -rw-r--r--. 1 root root system_u:object_r:tmpfs_t:s0 0 Dec 13 10:41 cgroup.threads
Signed-off-by: Ondrej Mosnacek omosnace@redhat.com Reviewed-by: Stephen Smalley sds@tycho.nsa.gov Signed-off-by: Paul Moore paul@paul-moore.com Signed-off-by: Sasha Levin sashal@kernel.org --- security/selinux/hooks.c | 9 ++++++++- 1 file changed, 8 insertions(+), 1 deletion(-)
diff --git a/security/selinux/hooks.c b/security/selinux/hooks.c index d293b546a2aa..9bd6f97ccd21 100644 --- a/security/selinux/hooks.c +++ b/security/selinux/hooks.c @@ -3265,12 +3265,16 @@ static int selinux_inode_setsecurity(struct inode *inode, const char *name, const void *value, size_t size, int flags) { struct inode_security_struct *isec = inode_security_novalidate(inode); + struct superblock_security_struct *sbsec = inode->i_sb->s_security; u32 newsid; int rc;
if (strcmp(name, XATTR_SELINUX_SUFFIX)) return -EOPNOTSUPP;
+ if (!(sbsec->flags & SBLABEL_MNT)) + return -EOPNOTSUPP; + if (!value || !size) return -EACCES;
@@ -5984,7 +5988,10 @@ static void selinux_inode_invalidate_secctx(struct inode *inode) */ static int selinux_inode_notifysecctx(struct inode *inode, void *ctx, u32 ctxlen) { - return selinux_inode_setsecurity(inode, XATTR_SELINUX_SUFFIX, ctx, ctxlen, 0); + int rc = selinux_inode_setsecurity(inode, XATTR_SELINUX_SUFFIX, + ctx, ctxlen, 0); + /* Do not return error when suppressing label (SBLABEL_MNT not set). */ + return rc == -EOPNOTSUPP ? 0 : rc; }
/*
From: Zumeng Chen zumeng.chen@gmail.com
[ Upstream commit ba2ffc96321c8433606ceeb85c9e722b8113e5a7 ]
Release fw_status, raw_fw_status, and tx_res_if when wl12xx_fetch_firmware failed instead of meaningless goto out to avoid the following memory leak reports(Only the last one listed):
unreferenced object 0xc28a9a00 (size 512): comm "kworker/0:4", pid 31298, jiffies 2783204 (age 203.290s) hex dump (first 32 bytes): 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 00 ................ backtrace: [<6624adab>] kmemleak_alloc+0x40/0x74 [<500ddb31>] kmem_cache_alloc_trace+0x1ac/0x270 [<db4d731d>] wl12xx_chip_wakeup+0xc4/0x1fc [wlcore] [<76c5db53>] wl1271_op_add_interface+0x4a4/0x8f4 [wlcore] [<cbf30777>] drv_add_interface+0xa4/0x1a0 [mac80211] [<65bac325>] ieee80211_reconfig+0x9c0/0x1644 [mac80211] [<2817c80e>] ieee80211_restart_work+0x90/0xc8 [mac80211] [<7e1d425a>] process_one_work+0x284/0x42c [<55f9432e>] worker_thread+0x2fc/0x48c [<abb582c6>] kthread+0x148/0x160 [<63144b13>] ret_from_fork+0x14/0x2c [< (null)>] (null) [<1f6e7715>] 0xffffffff
Signed-off-by: Zumeng Chen zumeng.chen@gmail.com Signed-off-by: Kalle Valo kvalo@codeaurora.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/net/wireless/ti/wlcore/main.c | 7 +++++-- 1 file changed, 5 insertions(+), 2 deletions(-)
diff --git a/drivers/net/wireless/ti/wlcore/main.c b/drivers/net/wireless/ti/wlcore/main.c index 5438975c7ff2..17d32ce5d16b 100644 --- a/drivers/net/wireless/ti/wlcore/main.c +++ b/drivers/net/wireless/ti/wlcore/main.c @@ -1058,8 +1058,11 @@ static int wl12xx_chip_wakeup(struct wl1271 *wl, bool plt) goto out;
ret = wl12xx_fetch_firmware(wl, plt); - if (ret < 0) - goto out; + if (ret < 0) { + kfree(wl->fw_status); + kfree(wl->raw_fw_status); + kfree(wl->tx_res_if); + }
out: return ret;
From: Rafael Ávila de Espíndola rafael@espindo.la
[ Upstream commit d071ae09a4a1414c1433d5ae9908959a7325b0ad ]
Accessing per-CPU variables is done by finding the offset of the variable in the per-CPU block and adding it to the address of the respective CPU's block.
Section 3.10.8 of ld.bfd's documentation states:
For expressions involving numbers, relative addresses and absolute addresses, ld follows these rules to evaluate terms:
Other binary operations, that is, between two relative addresses not in the same section, or between a relative address and an absolute address, first convert any non-absolute term to an absolute address before applying the operator."
Note that LLVM's linker does not adhere to the GNU ld's implementation and as such requires implicitly-absolute terms to be explicitly marked as absolute in the linker script. If not, it fails currently with:
ld.lld: error: ./arch/x86/kernel/vmlinux.lds:153: at least one side of the expression must be absolute ld.lld: error: ./arch/x86/kernel/vmlinux.lds:154: at least one side of the expression must be absolute Makefile:1040: recipe for target 'vmlinux' failed
This is not a functional change for ld.bfd which converts the term to an absolute symbol anyways as specified above.
Based on a previous submission by Tri Vo trong@android.com.
Reported-by: Dmitry Golovin dima@golovin.in Signed-off-by: Rafael Ávila de Espíndola rafael@espindo.la [ Update commit message per Boris' and Michael's suggestions. ] Signed-off-by: Nick Desaulniers ndesaulniers@google.com [ Massage commit message more, fix typos. ] Signed-off-by: Borislav Petkov bp@suse.de Tested-by: Dmitry Golovin dima@golovin.in Cc: "H. Peter Anvin" hpa@zytor.com Cc: Andy Lutomirski luto@kernel.org Cc: Brijesh Singh brijesh.singh@amd.com Cc: Cao Jin caoj.fnst@cn.fujitsu.com Cc: Ingo Molnar mingo@redhat.com Cc: Joerg Roedel jroedel@suse.de Cc: Masahiro Yamada yamada.masahiro@socionext.com Cc: Masami Hiramatsu mhiramat@kernel.org Cc: Thomas Gleixner tglx@linutronix.de Cc: Tri Vo trong@android.com Cc: dima@golovin.in Cc: morbo@google.com Cc: x86-ml x86@kernel.org Link: https://lkml.kernel.org/r/20181219190145.252035-1-ndesaulniers@google.com Signed-off-by: Sasha Levin sashal@kernel.org --- arch/x86/kernel/vmlinux.lds.S | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-)
diff --git a/arch/x86/kernel/vmlinux.lds.S b/arch/x86/kernel/vmlinux.lds.S index e783a5daaab2..55f04875293f 100644 --- a/arch/x86/kernel/vmlinux.lds.S +++ b/arch/x86/kernel/vmlinux.lds.S @@ -367,7 +367,7 @@ SECTIONS * Per-cpu symbols which need to be offset from __per_cpu_load * for the boot processor. */ -#define INIT_PER_CPU(x) init_per_cpu__##x = x + __per_cpu_load +#define INIT_PER_CPU(x) init_per_cpu__##x = ABSOLUTE(x) + __per_cpu_load INIT_PER_CPU(gdt_page); INIT_PER_CPU(irq_stack_union);
From: Ben Dooks ben.dooks@codethink.co.uk
[ Upstream commit e486df39305864604b7e25f2a95d51039517ac57 ]
The dma_desc->bytes_transferred counter tracks the number of bytes moved by the DMA channel. This is then used to calculate the information passed back in the in the tegra_dma_tx_status callback, which is usually fine.
When the DMA channel is configured as continous, then the bytes_transferred counter will increase over time and eventually overflow to become negative so the residue count will become invalid and the ALSA sound-dma code will report invalid hardware pointer values to the application. This results in some users becoming confused about the playout position and putting audio data in the wrong place.
To fix this issue, always ensure the bytes_transferred field is modulo the size of the request. We only do this for the case of the cyclic transfer done ISR as anyone attempting to move 2GiB of DMA data in one transfer is unlikely.
Note, we don't fix the issue that we should /never/ transfer a negative number of bytes so we could make those fields unsigned.
Reviewed-by: Dmitry Osipenko digetx@gmail.com Signed-off-by: Ben Dooks ben.dooks@codethink.co.uk Acked-by: Jon Hunter jonathanh@nvidia.com Signed-off-by: Vinod Koul vkoul@kernel.org Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/dma/tegra20-apb-dma.c | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-)
diff --git a/drivers/dma/tegra20-apb-dma.c b/drivers/dma/tegra20-apb-dma.c index 3722b9d8d9fe..22f7f0c68a48 100644 --- a/drivers/dma/tegra20-apb-dma.c +++ b/drivers/dma/tegra20-apb-dma.c @@ -635,7 +635,10 @@ static void handle_cont_sngl_cycle_dma_done(struct tegra_dma_channel *tdc,
sgreq = list_first_entry(&tdc->pending_sg_req, typeof(*sgreq), node); dma_desc = sgreq->dma_desc; - dma_desc->bytes_transferred += sgreq->req_len; + /* if we dma for long enough the transfer count will wrap */ + dma_desc->bytes_transferred = + (dma_desc->bytes_transferred + sgreq->req_len) % + dma_desc->bytes_requested;
/* Callback need to be call */ if (!dma_desc->cb_count)
From: Ville Syrjälä ville.syrjala@linux.intel.com
[ Upstream commit c978ae9bde582e82a04c63a4071701691dd8b35c ]
We aren't supposed to force a stop+start between every i2c msg when performing multi message transfers. This should eg. cause the DDC segment address to be reset back to 0 between writing the segment address and reading the actual EDID extension block.
To quote the E-DDC spec: "... this standard requires that the segment pointer be reset to 00h when a NO ACK or a STOP condition is received."
Since we're going to touch this might as well consult the I2C_M_STOP flag to determine whether we want to force the stop or not.
Cc: Brian Vincent brainn@gmail.com References: https://bugs.freedesktop.org/show_bug.cgi?id=108081 Signed-off-by: Ville Syrjälä ville.syrjala@linux.intel.com Link: https://patchwork.freedesktop.org/patch/msgid/20180928180403.22499-1-ville.s... Reviewed-by: Dhinakaran Pandiyan dhinakaran.pandiyan@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/gpu/drm/drm_dp_mst_topology.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/gpu/drm/drm_dp_mst_topology.c b/drivers/gpu/drm/drm_dp_mst_topology.c index b59441d109a5..4a959740058e 100644 --- a/drivers/gpu/drm/drm_dp_mst_topology.c +++ b/drivers/gpu/drm/drm_dp_mst_topology.c @@ -3069,6 +3069,7 @@ static int drm_dp_mst_i2c_xfer(struct i2c_adapter *adapter, struct i2c_msg *msgs msg.u.i2c_read.transactions[i].i2c_dev_id = msgs[i].addr; msg.u.i2c_read.transactions[i].num_bytes = msgs[i].len; msg.u.i2c_read.transactions[i].bytes = msgs[i].buf; + msg.u.i2c_read.transactions[i].no_stop_bit = !(msgs[i].flags & I2C_M_STOP); } msg.u.i2c_read.read_i2c_device_id = msgs[num - 1].addr; msg.u.i2c_read.num_bytes_read = msgs[num - 1].len;
From: Hans de Goede hdegoede@redhat.com
[ Upstream commit d693c008e3ca04db5916ff72e68ce661888a913b ]
Commit 53fa1f6e8a59 ("ACPI / video: Only default only_lcd to true on Win8-ready _desktops_") introduced chassis type detection, limiting the lcd_only check for the backlight to devices where the chassis-type indicates their is no builtin LCD panel.
The purpose of the lcd_only check is to avoid advertising a backlight interface on desktops, since skylake and newer machines seem to always have a backlight interface even if there is no LCD panel. The limiting of this check to desktops only was done to avoid breaking backlight support on some laptops which do not have the lcd flag set.
The Fujitsu ESPRIMO Q910 which is a compact (NUC like) desktop machine has a chassis type of 0x10 aka "Lunch Box". Without the lcd_only check we end up falsely advertising backlight/brightness control on this device. This commit extend the dmi_is_desktop check to return true for type 0x10 to fix this.
Fixes: 53fa1f6e8a59 ("ACPI / video: Only default only_lcd to true ...") Signed-off-by: Hans de Goede hdegoede@redhat.com Signed-off-by: Rafael J. Wysocki rafael.j.wysocki@intel.com Signed-off-by: Sasha Levin sashal@kernel.org --- drivers/acpi/acpi_video.c | 1 + 1 file changed, 1 insertion(+)
diff --git a/drivers/acpi/acpi_video.c b/drivers/acpi/acpi_video.c index d79e38abd6d9..ea0573176894 100644 --- a/drivers/acpi/acpi_video.c +++ b/drivers/acpi/acpi_video.c @@ -2088,6 +2088,7 @@ static bool dmi_is_desktop(void) case 0x05: /* Pizza Box */ case 0x06: /* Mini Tower */ case 0x07: /* Tower */ + case 0x10: /* Lunch Box */ case 0x11: /* Main Server Chassis */ return true; }
linux-stable-mirror@lists.linaro.org