linux-kernel.vger.kernel.org archive mirror
 help / color / mirror / Atom feed
* [PATCH -mm 0/3] minor kthread/signals cleanups and fix
@ 2015-10-03 18:13 Oleg Nesterov
  2015-10-03 18:13 ` [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal() Oleg Nesterov
                   ` (2 more replies)
  0 siblings, 3 replies; 8+ messages in thread
From: Oleg Nesterov @ 2015-10-03 18:13 UTC (permalink / raw)
  To: Andrew Morton
  Cc: David Woodhouse, Felipe Balbi, Markus Pargmann, Tejun Heo,
	linux-kernel, linux-mtd

On top of signals-kill-block_all_signals-and-unblock_all_signals.patch

Simple but untested, hopefully maintainers can ack or nack 1/3 at least.

Oleg.

 drivers/block/nbd.c                          |    9 ++-------
 drivers/usb/gadget/function/f_mass_storage.c |    4 +---
 fs/jffs2/background.c                        |    7 ++-----
 include/linux/sched.h                        |   21 ++++++++++++++++-----
 4 files changed, 21 insertions(+), 20 deletions(-)


^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal()
  2015-10-03 18:13 [PATCH -mm 0/3] minor kthread/signals cleanups and fix Oleg Nesterov
@ 2015-10-03 18:13 ` Oleg Nesterov
  2015-10-04 16:38   ` Tejun Heo
  2015-10-25 13:33   ` [PATCH -mm] signal-turn-dequeue_signal_lock-into-kernel_dequeue_signal-fix Oleg Nesterov
  2015-10-03 18:13 ` [PATCH 2/3] signal: introduce kernel_signal_stop() to fix jffs2_garbage_collect_thread() Oleg Nesterov
  2015-10-03 18:13 ` [PATCH 3/3] signal: remove jffs2_garbage_collect_thread()->allow_signal(SIGCONT) Oleg Nesterov
  2 siblings, 2 replies; 8+ messages in thread
From: Oleg Nesterov @ 2015-10-03 18:13 UTC (permalink / raw)
  To: Andrew Morton
  Cc: David Woodhouse, Felipe Balbi, Markus Pargmann, Tejun Heo,
	linux-kernel, linux-mtd

1. Rename dequeue_signal_lock() to kernel_dequeue_signal(). This
   matches another "for kthreads only" kernel_sigaction() helper.

2. Remove the "tsk" and "mask" arguments, they are always current
   and current->blocked. And it is simply wrong if tsk != current.

3. We could also remove the 3rd "siginfo_t *info" arg but it looks
   potentially useful. However we can simplify the callers if we
   change kernel_dequeue_signal() to accept info => NULL.

4. Remove _irqsave, it is never called from atomic context.

Signed-off-by: Oleg Nesterov <oleg@redhat.com>
---
 drivers/block/nbd.c                          |  9 ++-------
 drivers/usb/gadget/function/f_mass_storage.c |  4 +---
 fs/jffs2/background.c                        |  3 +--
 include/linux/sched.h                        | 11 ++++++-----
 4 files changed, 10 insertions(+), 17 deletions(-)

diff --git a/drivers/block/nbd.c b/drivers/block/nbd.c
index 293495a..214de17 100644
--- a/drivers/block/nbd.c
+++ b/drivers/block/nbd.c
@@ -432,9 +432,7 @@ static int nbd_thread_recv(struct nbd_device *nbd)
 	nbd->task_recv = NULL;
 
 	if (signal_pending(current)) {
-		siginfo_t info;
-
-		ret = dequeue_signal_lock(current, &current->blocked, &info);
+		ret = kernel_dequeue_signal(NULL);
 		dev_warn(nbd_to_dev(nbd), "pid %d, %s, got signal %d\n",
 			 task_pid_nr(current), current->comm, ret);
 		mutex_lock(&nbd->tx_lock);
@@ -545,11 +543,8 @@ static int nbd_thread_send(void *data)
 					 !list_empty(&nbd->waiting_queue));
 
 		if (signal_pending(current)) {
-			siginfo_t info;
-			int ret;
+			int ret = kernel_dequeue_signal(NULL);
 
-			ret = dequeue_signal_lock(current, &current->blocked,
-						  &info);
 			dev_warn(nbd_to_dev(nbd), "pid %d, %s, got signal %d\n",
 				 task_pid_nr(current), current->comm, ret);
 			mutex_lock(&nbd->tx_lock);
diff --git a/drivers/usb/gadget/function/f_mass_storage.c b/drivers/usb/gadget/function/f_mass_storage.c
index a6eb537..9d1e3b3 100644
--- a/drivers/usb/gadget/function/f_mass_storage.c
+++ b/drivers/usb/gadget/function/f_mass_storage.c
@@ -2347,7 +2347,6 @@ static void fsg_disable(struct usb_function *f)
 
 static void handle_exception(struct fsg_common *common)
 {
-	siginfo_t		info;
 	int			i;
 	struct fsg_buffhd	*bh;
 	enum fsg_state		old_state;
@@ -2359,8 +2358,7 @@ static void handle_exception(struct fsg_common *common)
 	 * into a high-priority EXIT exception.
 	 */
 	for (;;) {
-		int sig =
-			dequeue_signal_lock(current, &current->blocked, &info);
+		int sig = kernel_dequeue_signal(NULL);
 		if (!sig)
 			break;
 		if (sig != SIGUSR1) {
diff --git a/fs/jffs2/background.c b/fs/jffs2/background.c
index bb9cebc..f3145fd 100644
--- a/fs/jffs2/background.c
+++ b/fs/jffs2/background.c
@@ -121,13 +121,12 @@ static int jffs2_garbage_collect_thread(void *_c)
 		/* Put_super will send a SIGKILL and then wait on the sem.
 		 */
 		while (signal_pending(current) || freezing(current)) {
-			siginfo_t info;
 			unsigned long signr;
 
 			if (try_to_freeze())
 				goto again;
 
-			signr = dequeue_signal_lock(current, &current->blocked, &info);
+			signr = kernel_dequeue_signal(NULL);
 
 			switch(signr) {
 			case SIGSTOP:
diff --git a/include/linux/sched.h b/include/linux/sched.h
index 8c3fa80..e714539 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -2464,14 +2464,15 @@ extern void ignore_signals(struct task_struct *);
 extern void flush_signal_handlers(struct task_struct *, int force_default);
 extern int dequeue_signal(struct task_struct *tsk, sigset_t *mask, siginfo_t *info);
 
-static inline int dequeue_signal_lock(struct task_struct *tsk, sigset_t *mask, siginfo_t *info)
+static inline int kernel_dequeue_signal(siginfo_t *info)
 {
-	unsigned long flags;
+	struct task_struct *tsk = current;
+	siginfo_t __info;
 	int ret;
 
-	spin_lock_irqsave(&tsk->sighand->siglock, flags);
-	ret = dequeue_signal(tsk, mask, info);
-	spin_unlock_irqrestore(&tsk->sighand->siglock, flags);
+	spin_lock_irq(&tsk->sighand->siglock);
+	ret = dequeue_signal(tsk, &tsk->blocked, info ?: &__info);
+	spin_unlock_irq(&tsk->sighand->siglock);
 
 	return ret;
 }
-- 
2.4.3


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [PATCH 2/3] signal: introduce kernel_signal_stop() to fix jffs2_garbage_collect_thread()
  2015-10-03 18:13 [PATCH -mm 0/3] minor kthread/signals cleanups and fix Oleg Nesterov
  2015-10-03 18:13 ` [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal() Oleg Nesterov
@ 2015-10-03 18:13 ` Oleg Nesterov
  2015-10-04 17:28   ` Tejun Heo
  2015-10-03 18:13 ` [PATCH 3/3] signal: remove jffs2_garbage_collect_thread()->allow_signal(SIGCONT) Oleg Nesterov
  2 siblings, 1 reply; 8+ messages in thread
From: Oleg Nesterov @ 2015-10-03 18:13 UTC (permalink / raw)
  To: Andrew Morton
  Cc: David Woodhouse, Felipe Balbi, Markus Pargmann, Tejun Heo,
	linux-kernel, linux-mtd

jffs2_garbage_collect_thread() can race with SIGCONT and sleep in
TASK_STOPPED state after it was already sent. Add the new helper,
kernel_signal_stop(), which does this correctly.

Signed-off-by: Oleg Nesterov <oleg@redhat.com>
---
 fs/jffs2/background.c |  3 +--
 include/linux/sched.h | 10 ++++++++++
 2 files changed, 11 insertions(+), 2 deletions(-)

diff --git a/fs/jffs2/background.c b/fs/jffs2/background.c
index f3145fd..53cc735 100644
--- a/fs/jffs2/background.c
+++ b/fs/jffs2/background.c
@@ -132,8 +132,7 @@ static int jffs2_garbage_collect_thread(void *_c)
 			case SIGSTOP:
 				jffs2_dbg(1, "%s(): SIGSTOP received\n",
 					  __func__);
-				set_current_state(TASK_STOPPED);
-				schedule();
+				kernel_signal_stop();
 				break;
 
 			case SIGKILL:
diff --git a/include/linux/sched.h b/include/linux/sched.h
index e714539..56e688c 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -2477,6 +2477,16 @@ static inline int kernel_dequeue_signal(siginfo_t *info)
 	return ret;
 }
 
+static inline void kernel_signal_stop(void)
+{
+	spin_lock_irq(&current->sighand->siglock);
+	if (current->jobctl & JOBCTL_STOP_DEQUEUED)
+		__set_current_state(TASK_STOPPED);
+	spin_unlock_irq(&current->sighand->siglock);
+
+	schedule();
+}
+
 extern void release_task(struct task_struct * p);
 extern int send_sig_info(int, struct siginfo *, struct task_struct *);
 extern int force_sigsegv(int, struct task_struct *);
-- 
2.4.3


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* [PATCH 3/3] signal: remove jffs2_garbage_collect_thread()->allow_signal(SIGCONT)
  2015-10-03 18:13 [PATCH -mm 0/3] minor kthread/signals cleanups and fix Oleg Nesterov
  2015-10-03 18:13 ` [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal() Oleg Nesterov
  2015-10-03 18:13 ` [PATCH 2/3] signal: introduce kernel_signal_stop() to fix jffs2_garbage_collect_thread() Oleg Nesterov
@ 2015-10-03 18:13 ` Oleg Nesterov
  2015-10-04 17:28   ` Tejun Heo
  2 siblings, 1 reply; 8+ messages in thread
From: Oleg Nesterov @ 2015-10-03 18:13 UTC (permalink / raw)
  To: Andrew Morton
  Cc: David Woodhouse, Felipe Balbi, Markus Pargmann, Tejun Heo,
	linux-kernel, linux-mtd

jffs2_garbage_collect_thread() does allow_signal(SIGCONT) for no reason,
SIGCONT will wake a stopped task up even if it is ignored.

Signed-off-by: Oleg Nesterov <oleg@redhat.com>
---
 fs/jffs2/background.c | 1 -
 1 file changed, 1 deletion(-)

diff --git a/fs/jffs2/background.c b/fs/jffs2/background.c
index 53cc735..e5c1783 100644
--- a/fs/jffs2/background.c
+++ b/fs/jffs2/background.c
@@ -80,7 +80,6 @@ static int jffs2_garbage_collect_thread(void *_c)
 	siginitset(&hupmask, sigmask(SIGHUP));
 	allow_signal(SIGKILL);
 	allow_signal(SIGSTOP);
-	allow_signal(SIGCONT);
 	allow_signal(SIGHUP);
 
 	c->gc_task = current;
-- 
2.4.3


^ permalink raw reply related	[flat|nested] 8+ messages in thread

* Re: [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal()
  2015-10-03 18:13 ` [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal() Oleg Nesterov
@ 2015-10-04 16:38   ` Tejun Heo
  2015-10-25 13:33   ` [PATCH -mm] signal-turn-dequeue_signal_lock-into-kernel_dequeue_signal-fix Oleg Nesterov
  1 sibling, 0 replies; 8+ messages in thread
From: Tejun Heo @ 2015-10-04 16:38 UTC (permalink / raw)
  To: Oleg Nesterov
  Cc: Andrew Morton, David Woodhouse, Felipe Balbi, Markus Pargmann,
	linux-kernel, linux-mtd

On Sat, Oct 03, 2015 at 08:13:36PM +0200, Oleg Nesterov wrote:
> 1. Rename dequeue_signal_lock() to kernel_dequeue_signal(). This
>    matches another "for kthreads only" kernel_sigaction() helper.
> 
> 2. Remove the "tsk" and "mask" arguments, they are always current
>    and current->blocked. And it is simply wrong if tsk != current.
> 
> 3. We could also remove the 3rd "siginfo_t *info" arg but it looks
>    potentially useful. However we can simplify the callers if we
>    change kernel_dequeue_signal() to accept info => NULL.
> 
> 4. Remove _irqsave, it is never called from atomic context.
> 
> Signed-off-by: Oleg Nesterov <oleg@redhat.com>

FWIW, looks good to me.

Reviewed-by: Tejun Heo <tj@kernel.org>

Thanks.

-- 
tejun

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH 2/3] signal: introduce kernel_signal_stop() to fix jffs2_garbage_collect_thread()
  2015-10-03 18:13 ` [PATCH 2/3] signal: introduce kernel_signal_stop() to fix jffs2_garbage_collect_thread() Oleg Nesterov
@ 2015-10-04 17:28   ` Tejun Heo
  0 siblings, 0 replies; 8+ messages in thread
From: Tejun Heo @ 2015-10-04 17:28 UTC (permalink / raw)
  To: Oleg Nesterov
  Cc: Andrew Morton, David Woodhouse, Felipe Balbi, Markus Pargmann,
	linux-kernel, linux-mtd

On Sat, Oct 03, 2015 at 08:13:38PM +0200, Oleg Nesterov wrote:
> jffs2_garbage_collect_thread() can race with SIGCONT and sleep in
> TASK_STOPPED state after it was already sent. Add the new helper,
> kernel_signal_stop(), which does this correctly.
> 
> Signed-off-by: Oleg Nesterov <oleg@redhat.com>

Reviewed-by: Tejun Heo <tj@kernel.org>

Thanks.

-- 
tejun

^ permalink raw reply	[flat|nested] 8+ messages in thread

* Re: [PATCH 3/3] signal: remove jffs2_garbage_collect_thread()->allow_signal(SIGCONT)
  2015-10-03 18:13 ` [PATCH 3/3] signal: remove jffs2_garbage_collect_thread()->allow_signal(SIGCONT) Oleg Nesterov
@ 2015-10-04 17:28   ` Tejun Heo
  0 siblings, 0 replies; 8+ messages in thread
From: Tejun Heo @ 2015-10-04 17:28 UTC (permalink / raw)
  To: Oleg Nesterov
  Cc: Andrew Morton, David Woodhouse, Felipe Balbi, Markus Pargmann,
	linux-kernel, linux-mtd

On Sat, Oct 03, 2015 at 08:13:41PM +0200, Oleg Nesterov wrote:
> jffs2_garbage_collect_thread() does allow_signal(SIGCONT) for no reason,
> SIGCONT will wake a stopped task up even if it is ignored.
> 
> Signed-off-by: Oleg Nesterov <oleg@redhat.com>

Reviewed-by: Tejun Heo <tj@kernel.org>

Thanks.

-- 
tejun

^ permalink raw reply	[flat|nested] 8+ messages in thread

* [PATCH -mm] signal-turn-dequeue_signal_lock-into-kernel_dequeue_signal-fix
  2015-10-03 18:13 ` [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal() Oleg Nesterov
  2015-10-04 16:38   ` Tejun Heo
@ 2015-10-25 13:33   ` Oleg Nesterov
  1 sibling, 0 replies; 8+ messages in thread
From: Oleg Nesterov @ 2015-10-25 13:33 UTC (permalink / raw)
  To: Andrew Morton
  Cc: David Woodhouse, Felipe Balbi, Markus Pargmann, Tejun Heo,
	linux-kernel, linux-mtd

Andrew,

As Markus reports (thanks!)

	signal-turn-dequeue_signal_lock-into-kernel_dequeue_signal.patch

conflicts with the recent change in Linus' tree,

> I just realised that this patch will conflict with a fixup patch for nbd
> that will be included in rc7.
>
> dcc909d90ccd (nbd: Add locking for tasks)
>
> I think there is basically one new instance of dequeue_signal_lock() that
> needs to be replaced with kernel_dequeue_signal().

Unless I missed something, this new dequeue_signal_lock() should simply
die, but lets fix the conflict first.


--- a/drivers/block/nbd.c
+++ b/drivers/block/nbd.c
@@ -592,10 +592,8 @@ static int nbd_thread_send(void *data)
 	spin_unlock_irqrestore(&nbd->tasks_lock, flags);
 
 	/* Clear maybe pending signals */
-	if (signal_pending(current)) {
-		siginfo_t info;
-		dequeue_signal_lock(current, &current->blocked, &info);
-	}
+	if (signal_pending(current))
+		kernel_dequeue_signal(NULL);
 
 	return 0;
 }


^ permalink raw reply	[flat|nested] 8+ messages in thread

end of thread, other threads:[~2015-10-25 12:37 UTC | newest]

Thread overview: 8+ messages (download: mbox.gz / follow: Atom feed)
-- links below jump to the message on this page --
2015-10-03 18:13 [PATCH -mm 0/3] minor kthread/signals cleanups and fix Oleg Nesterov
2015-10-03 18:13 ` [PATCH 1/3] signal: turn dequeue_signal_lock() into kernel_dequeue_signal() Oleg Nesterov
2015-10-04 16:38   ` Tejun Heo
2015-10-25 13:33   ` [PATCH -mm] signal-turn-dequeue_signal_lock-into-kernel_dequeue_signal-fix Oleg Nesterov
2015-10-03 18:13 ` [PATCH 2/3] signal: introduce kernel_signal_stop() to fix jffs2_garbage_collect_thread() Oleg Nesterov
2015-10-04 17:28   ` Tejun Heo
2015-10-03 18:13 ` [PATCH 3/3] signal: remove jffs2_garbage_collect_thread()->allow_signal(SIGCONT) Oleg Nesterov
2015-10-04 17:28   ` Tejun Heo

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox;
as well as URLs for NNTP newsgroup(s).