public inbox for linux-kernel@vger.kernel.org
 help / color / mirror / Atom feed
* [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try
@ 2009-06-15 15:27 Lennart Poettering
  2009-06-15 15:37 ` [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag tip-bot for Lennart Poettering
  2009-06-16  9:05 ` [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Mike Galbraith
  0 siblings, 2 replies; 9+ messages in thread
From: Lennart Poettering @ 2009-06-15 15:27 UTC (permalink / raw)
  To: Peter Zijlstra, Ingo Molnar; +Cc: linux-kernel

(this is the fourth version of the patch, only change is that I added
the missing Signed-off-by line, as Ingo requested)

This patch introduces a new flag SCHED_RESET_ON_FORK which can be passed
to the kernel via sched_setscheduler(), ORed in the policy parameter. If
set this will make sure that when the process forks a) the scheduling
priority is reset to DEFAULT_PRIO if it was higher and b) the scheduling
policy is reset to SCHED_NORMAL if it was either SCHED_FIFO or SCHED_RR.

Why have this?

Currently, if a process is real-time scheduled this will 'leak' to all
its child processes. For security reasons it is often (always?) a good
idea to make sure that if a process acquires RT scheduling this is
confined to this process and only this process. More specifically this
makes the per-process resource limit RLIMIT_RTTIME useful for security
purposes, because it makes it impossible to use a fork bomb to
circumvent the per-process RLIMIT_RTTIME accounting.

This feature is also useful for tools like 'renice' which can then
change the nice level of a process without having this spill to all its
child processes.

Why expose this via sched_setscheduler() and not other syscalls such as
prctl() or sched_setparam()?

prctl() does not take a pid parameter. Due to that it would be
impossible to modify this flag for other processes than the current one.

The struct passed to sched_setparam() can unfortunately not be extended
without breaking compatibility, since sched_setparam() lacks a size
parameter.

How to use this from userspace? In your RT program simply replace this:

  sched_setscheduler(pid, SCHED_FIFO, &param);

by this:

  sched_setscheduler(pid, SCHED_FIFO|SCHED_RESET_ON_FORK, &param);

Lennart

Signed-off-by: Lennart Poettering <lennart@poettering.net>
---
 include/linux/sched.h |    6 ++++++
 kernel/sched.c        |   47 ++++++++++++++++++++++++++++++++++++++---------
 2 files changed, 44 insertions(+), 9 deletions(-)

diff --git a/include/linux/sched.h b/include/linux/sched.h
index 83f3564..bd503ce 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -38,6 +38,8 @@
 #define SCHED_BATCH		3
 /* SCHED_ISO: reserved but not implemented yet */
 #define SCHED_IDLE		5
+/* Can be ORed in to make sure the process is reverted back to SCHED_NORMAL on fork */
+#define SCHED_RESET_ON_FORK     0x40000000
 
 #ifdef __KERNEL__
 
@@ -1209,6 +1211,10 @@ struct task_struct {
 	unsigned did_exec:1;
 	unsigned in_execve:1;	/* Tell the LSMs that the process is doing an
 				 * execve */
+
+	/* Revert to default priority/policy when forking */
+	unsigned sched_reset_on_fork:1;
+
 	pid_t pid;
 	pid_t tgid;
 
diff --git a/kernel/sched.c b/kernel/sched.c
index 8ec9d13..1db3e4a 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2613,12 +2613,26 @@ void sched_fork(struct task_struct *p, int clone_flags)
 	set_task_cpu(p, cpu);
 
 	/*
-	 * Make sure we do not leak PI boosting priority to the child:
+	 * Revert to default priority/policy on fork if requested. Make sure we
+	 * do not leak PI boosting priority to the child.
 	 */
-	p->prio = current->normal_prio;
+	if (current->sched_reset_on_fork &&
+			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
+		p->policy = SCHED_NORMAL;
+
+	if (current->sched_reset_on_fork &&
+			(current->normal_prio < DEFAULT_PRIO))
+		p->prio = DEFAULT_PRIO;
+	else
+		p->prio = current->normal_prio;
+
 	if (!rt_prio(p->prio))
 		p->sched_class = &fair_sched_class;
 
+	/* We don't need the reset flag anymore after the fork. It has
+	 * fulfilled its duty. */
+	p->sched_reset_on_fork = 0;
+
 #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
 	if (likely(sched_info_on()))
 		memset(&p->sched_info, 0, sizeof(p->sched_info));
@@ -6094,17 +6108,25 @@ static int __sched_setscheduler(struct task_struct *p, int policy,
 	unsigned long flags;
 	const struct sched_class *prev_class = p->sched_class;
 	struct rq *rq;
+	int reset_on_fork;
 
 	/* may grab non-irq protected spin_locks */
 	BUG_ON(in_interrupt());
 recheck:
 	/* double check policy once rq lock held */
-	if (policy < 0)
+	if (policy < 0) {
+		reset_on_fork = p->sched_reset_on_fork;
 		policy = oldpolicy = p->policy;
-	else if (policy != SCHED_FIFO && policy != SCHED_RR &&
-			policy != SCHED_NORMAL && policy != SCHED_BATCH &&
-			policy != SCHED_IDLE)
-		return -EINVAL;
+	} else {
+		reset_on_fork = !!(policy & SCHED_RESET_ON_FORK);
+		policy &= ~SCHED_RESET_ON_FORK;
+
+		if (policy != SCHED_FIFO && policy != SCHED_RR &&
+				policy != SCHED_NORMAL && policy != SCHED_BATCH &&
+				policy != SCHED_IDLE)
+			return -EINVAL;
+	}
+
 	/*
 	 * Valid priorities for SCHED_FIFO and SCHED_RR are
 	 * 1..MAX_USER_RT_PRIO-1, valid priority for SCHED_NORMAL,
@@ -6148,6 +6170,10 @@ recheck:
 		/* can't change other user's priorities */
 		if (!check_same_owner(p))
 			return -EPERM;
+
+		/* normal users shall not reset the sched_reset_on_fork flag */
+		if (p->sched_reset_on_fork && !reset_on_fork)
+			return -EPERM;
 	}
 
 	if (user) {
@@ -6191,6 +6217,8 @@ recheck:
 	if (running)
 		p->sched_class->put_prev_task(rq, p);
 
+	p->sched_reset_on_fork = reset_on_fork;
+
 	oldprio = p->prio;
 	__setscheduler(rq, p, policy, param->sched_priority);
 
@@ -6307,14 +6335,15 @@ SYSCALL_DEFINE1(sched_getscheduler, pid_t, pid)
 	if (p) {
 		retval = security_task_getscheduler(p);
 		if (!retval)
-			retval = p->policy;
+			retval = p->policy
+				| (p->sched_reset_on_fork ? SCHED_RESET_ON_FORK : 0);
 	}
 	read_unlock(&tasklist_lock);
 	return retval;
 }
 
 /**
- * sys_sched_getscheduler - get the RT priority of a thread
+ * sys_sched_getparam - get the RT priority of a thread
  * @pid: the pid in question.
  * @param: structure containing the RT priority.
  */
-- 
1.6.2.2



Lennart

-- 
Lennart Poettering                        Red Hat, Inc.
lennart [at] poettering [dot] net
http://0pointer.net/lennart/           GnuPG 0x1A015CC4

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

* [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag
  2009-06-15 15:27 [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Lennart Poettering
@ 2009-06-15 15:37 ` tip-bot for Lennart Poettering
  2009-06-16  9:05 ` [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Mike Galbraith
  1 sibling, 0 replies; 9+ messages in thread
From: tip-bot for Lennart Poettering @ 2009-06-15 15:37 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: linux-kernel, hpa, mingo, a.p.zijlstra, lennart, tglx, mingo

Commit-ID:  ca94c442535a44d508c99a77e54f21a59f4fc462
Gitweb:     http://git.kernel.org/tip/ca94c442535a44d508c99a77e54f21a59f4fc462
Author:     Lennart Poettering <lennart@poettering.net>
AuthorDate: Mon, 15 Jun 2009 17:17:47 +0200
Committer:  Ingo Molnar <mingo@elte.hu>
CommitDate: Mon, 15 Jun 2009 17:31:59 +0200

sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag

This patch introduces a new flag SCHED_RESET_ON_FORK which can be passed
to the kernel via sched_setscheduler(), ORed in the policy parameter. If
set this will make sure that when the process forks a) the scheduling
priority is reset to DEFAULT_PRIO if it was higher and b) the scheduling
policy is reset to SCHED_NORMAL if it was either SCHED_FIFO or SCHED_RR.

Why have this?

Currently, if a process is real-time scheduled this will 'leak' to all
its child processes. For security reasons it is often (always?) a good
idea to make sure that if a process acquires RT scheduling this is
confined to this process and only this process. More specifically this
makes the per-process resource limit RLIMIT_RTTIME useful for security
purposes, because it makes it impossible to use a fork bomb to
circumvent the per-process RLIMIT_RTTIME accounting.

This feature is also useful for tools like 'renice' which can then
change the nice level of a process without having this spill to all its
child processes.

Why expose this via sched_setscheduler() and not other syscalls such as
prctl() or sched_setparam()?

prctl() does not take a pid parameter. Due to that it would be
impossible to modify this flag for other processes than the current one.

The struct passed to sched_setparam() can unfortunately not be extended
without breaking compatibility, since sched_setparam() lacks a size
parameter.

How to use this from userspace? In your RT program simply replace this:

  sched_setscheduler(pid, SCHED_FIFO, &param);

by this:

  sched_setscheduler(pid, SCHED_FIFO|SCHED_RESET_ON_FORK, &param);

Signed-off-by: Lennart Poettering <lennart@poettering.net>
Acked-by: Peter Zijlstra <a.p.zijlstra@chello.nl>
LKML-Reference: <20090615152714.GA29092@tango.0pointer.de>
Signed-off-by: Ingo Molnar <mingo@elte.hu>


---
 include/linux/sched.h |    6 ++++++
 kernel/sched.c        |   49 ++++++++++++++++++++++++++++++++++++++++---------
 2 files changed, 46 insertions(+), 9 deletions(-)

diff --git a/include/linux/sched.h b/include/linux/sched.h
index 4896fdf..d4a2c66 100644
--- a/include/linux/sched.h
+++ b/include/linux/sched.h
@@ -38,6 +38,8 @@
 #define SCHED_BATCH		3
 /* SCHED_ISO: reserved but not implemented yet */
 #define SCHED_IDLE		5
+/* Can be ORed in to make sure the process is reverted back to SCHED_NORMAL on fork */
+#define SCHED_RESET_ON_FORK     0x40000000
 
 #ifdef __KERNEL__
 
@@ -1209,6 +1211,10 @@ struct task_struct {
 	unsigned did_exec:1;
 	unsigned in_execve:1;	/* Tell the LSMs that the process is doing an
 				 * execve */
+
+	/* Revert to default priority/policy when forking */
+	unsigned sched_reset_on_fork:1;
+
 	pid_t pid;
 	pid_t tgid;
 
diff --git a/kernel/sched.c b/kernel/sched.c
index 8ec9d13..32e6ede 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2613,12 +2613,28 @@ void sched_fork(struct task_struct *p, int clone_flags)
 	set_task_cpu(p, cpu);
 
 	/*
-	 * Make sure we do not leak PI boosting priority to the child:
+	 * Revert to default priority/policy on fork if requested. Make sure we
+	 * do not leak PI boosting priority to the child.
 	 */
-	p->prio = current->normal_prio;
+	if (current->sched_reset_on_fork &&
+			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
+		p->policy = SCHED_NORMAL;
+
+	if (current->sched_reset_on_fork &&
+			(current->normal_prio < DEFAULT_PRIO))
+		p->prio = DEFAULT_PRIO;
+	else
+		p->prio = current->normal_prio;
+
 	if (!rt_prio(p->prio))
 		p->sched_class = &fair_sched_class;
 
+	/*
+	 * We don't need the reset flag anymore after the fork. It has
+	 * fulfilled its duty:
+	 */
+	p->sched_reset_on_fork = 0;
+
 #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
 	if (likely(sched_info_on()))
 		memset(&p->sched_info, 0, sizeof(p->sched_info));
@@ -6094,17 +6110,25 @@ static int __sched_setscheduler(struct task_struct *p, int policy,
 	unsigned long flags;
 	const struct sched_class *prev_class = p->sched_class;
 	struct rq *rq;
+	int reset_on_fork;
 
 	/* may grab non-irq protected spin_locks */
 	BUG_ON(in_interrupt());
 recheck:
 	/* double check policy once rq lock held */
-	if (policy < 0)
+	if (policy < 0) {
+		reset_on_fork = p->sched_reset_on_fork;
 		policy = oldpolicy = p->policy;
-	else if (policy != SCHED_FIFO && policy != SCHED_RR &&
-			policy != SCHED_NORMAL && policy != SCHED_BATCH &&
-			policy != SCHED_IDLE)
-		return -EINVAL;
+	} else {
+		reset_on_fork = !!(policy & SCHED_RESET_ON_FORK);
+		policy &= ~SCHED_RESET_ON_FORK;
+
+		if (policy != SCHED_FIFO && policy != SCHED_RR &&
+				policy != SCHED_NORMAL && policy != SCHED_BATCH &&
+				policy != SCHED_IDLE)
+			return -EINVAL;
+	}
+
 	/*
 	 * Valid priorities for SCHED_FIFO and SCHED_RR are
 	 * 1..MAX_USER_RT_PRIO-1, valid priority for SCHED_NORMAL,
@@ -6148,6 +6172,10 @@ recheck:
 		/* can't change other user's priorities */
 		if (!check_same_owner(p))
 			return -EPERM;
+
+		/* Normal users shall not reset the sched_reset_on_fork flag */
+		if (p->sched_reset_on_fork && !reset_on_fork)
+			return -EPERM;
 	}
 
 	if (user) {
@@ -6191,6 +6219,8 @@ recheck:
 	if (running)
 		p->sched_class->put_prev_task(rq, p);
 
+	p->sched_reset_on_fork = reset_on_fork;
+
 	oldprio = p->prio;
 	__setscheduler(rq, p, policy, param->sched_priority);
 
@@ -6307,14 +6337,15 @@ SYSCALL_DEFINE1(sched_getscheduler, pid_t, pid)
 	if (p) {
 		retval = security_task_getscheduler(p);
 		if (!retval)
-			retval = p->policy;
+			retval = p->policy
+				| (p->sched_reset_on_fork ? SCHED_RESET_ON_FORK : 0);
 	}
 	read_unlock(&tasklist_lock);
 	return retval;
 }
 
 /**
- * sys_sched_getscheduler - get the RT priority of a thread
+ * sys_sched_getparam - get the RT priority of a thread
  * @pid: the pid in question.
  * @param: structure containing the RT priority.
  */

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

* Re: [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try
  2009-06-15 15:27 [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Lennart Poettering
  2009-06-15 15:37 ` [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag tip-bot for Lennart Poettering
@ 2009-06-16  9:05 ` Mike Galbraith
  2009-06-16 16:47   ` Lennart Poettering
  2009-06-17 10:32   ` [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag, fix tip-bot for Mike Galbraith
  1 sibling, 2 replies; 9+ messages in thread
From: Mike Galbraith @ 2009-06-16  9:05 UTC (permalink / raw)
  To: Lennart Poettering; +Cc: Peter Zijlstra, Ingo Molnar, linux-kernel

On Mon, 2009-06-15 at 17:27 +0200, Lennart Poettering wrote: 
> (this is the fourth version of the patch, only change is that I added
> the missing Signed-off-by line, as Ingo requested)
> 
> This patch introduces a new flag SCHED_RESET_ON_FORK which can be passed
> to the kernel via sched_setscheduler(), ORed in the policy parameter. If
> set this will make sure that when the process forks a) the scheduling
> priority is reset to DEFAULT_PRIO if it was higher and b) the scheduling
> policy is reset to SCHED_NORMAL if it was either SCHED_FIFO or SCHED_RR.
> 
> Why have this?
> 
> Currently, if a process is real-time scheduled this will 'leak' to all
> its child processes. For security reasons it is often (always?) a good
> idea to make sure that if a process acquires RT scheduling this is
> confined to this process and only this process. More specifically this
> makes the per-process resource limit RLIMIT_RTTIME useful for security
> purposes, because it makes it impossible to use a fork bomb to
> circumvent the per-process RLIMIT_RTTIME accounting.
> 
> This feature is also useful for tools like 'renice' which can then
> change the nice level of a process without having this spill to all its
> child processes.

That didn't work for me, reniced tasks with the flag set retained their
-nice status.  See patchlet and comments below. 

> diff --git a/kernel/sched.c b/kernel/sched.c
> index 8ec9d13..1db3e4a 100644
> --- a/kernel/sched.c
> +++ b/kernel/sched.c
> @@ -2613,12 +2613,26 @@ void sched_fork(struct task_struct *p, int clone_flags)
>  	set_task_cpu(p, cpu);
>  
>  	/*
> -	 * Make sure we do not leak PI boosting priority to the child:
> +	 * Revert to default priority/policy on fork if requested. Make sure we
> +	 * do not leak PI boosting priority to the child.
>  	 */
> -	p->prio = current->normal_prio;

Nit: that comment/assignment was placed there to make sure that readers
knew that this specific line was critical to PI.  Now, it's mixed in
with something unrelated.
 
> +	if (current->sched_reset_on_fork &&
> +			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
> +		p->policy = SCHED_NORMAL;
> +
> +	if (current->sched_reset_on_fork &&
> +			(current->normal_prio < DEFAULT_PRIO))
> +		p->prio = DEFAULT_PRIO;
> +	else
> +		p->prio = current->normal_prio;
> +

I think it's cleaner to keep reset_on_fork functionality separate.
Thoughts on the below?

Make SCHED_RESET_ON_FORK to DTRT for reniced tasks, and make the sched_fork()
SCHED_RESET_ON_FORK bits a self-contained unlikely code block.

Signed-off-by: Mike Galbraith <efault@gmx.de>

 kernel/sched.c |   39 +++++++++++++++++++++++----------------
 1 files changed, 23 insertions(+), 16 deletions(-)

diff --git a/kernel/sched.c b/kernel/sched.c
index 80636ed..cb6bbc6 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2613,28 +2613,35 @@ void sched_fork(struct task_struct *p, int clone_flags)
 	set_task_cpu(p, cpu);
 
 	/*
-	 * Revert to default priority/policy on fork if requested. Make sure we
-	 * do not leak PI boosting priority to the child.
+	 * Make sure we do not leak PI boosting priority to the child.
 	 */
-	if (current->sched_reset_on_fork &&
-			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
-		p->policy = SCHED_NORMAL;
+	p->prio = current->normal_prio;
 
-	if (current->sched_reset_on_fork &&
-			(current->normal_prio < DEFAULT_PRIO))
-		p->prio = DEFAULT_PRIO;
-	else
-		p->prio = current->normal_prio;
+	/*
+	 * Revert to default priority/policy on fork if requested.
+	 */
+	if (unlikely(p->sched_reset_on_fork)) {
+		if (p->policy == SCHED_FIFO || p->policy == SCHED_RR)
+			p->policy = SCHED_NORMAL;
+
+		if (p->normal_prio < DEFAULT_PRIO)
+			p->prio = DEFAULT_PRIO;
+
+		if (PRIO_TO_NICE(p->static_prio) < 0) {
+			p->static_prio = NICE_TO_PRIO(0);
+			set_load_weight(p);
+		}
+
+		/*
+		 * We don't need the reset flag anymore after the fork. It has
+		 * fulfilled its duty:
+		 */
+		p->sched_reset_on_fork = 0;
+	}
 
 	if (!rt_prio(p->prio))
 		p->sched_class = &fair_sched_class;
 
-	/*
-	 * We don't need the reset flag anymore after the fork. It has
-	 * fulfilled its duty:
-	 */
-	p->sched_reset_on_fork = 0;
-
 #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
 	if (likely(sched_info_on()))
 		memset(&p->sched_info, 0, sizeof(p->sched_info));



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

* Re: [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try
  2009-06-16  9:05 ` [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Mike Galbraith
@ 2009-06-16 16:47   ` Lennart Poettering
  2009-06-17  8:46     ` [patch 1/2] " Mike Galbraith
  2009-06-17 10:32   ` [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag, fix tip-bot for Mike Galbraith
  1 sibling, 1 reply; 9+ messages in thread
From: Lennart Poettering @ 2009-06-16 16:47 UTC (permalink / raw)
  To: Mike Galbraith; +Cc: Peter Zijlstra, Ingo Molnar, linux-kernel

On Tue, 16.06.09 11:05, Mike Galbraith (efault@gmx.de) wrote:

> I think it's cleaner to keep reset_on_fork functionality separate.
> Thoughts on the below?

Looks good to me!

Lennart

> Make SCHED_RESET_ON_FORK to DTRT for reniced tasks, and make the sched_fork()
> SCHED_RESET_ON_FORK bits a self-contained unlikely code block.
> 
> Signed-off-by: Mike Galbraith <efault@gmx.de>
> 
>  kernel/sched.c |   39 +++++++++++++++++++++++----------------
>  1 files changed, 23 insertions(+), 16 deletions(-)
> 
> diff --git a/kernel/sched.c b/kernel/sched.c
> index 80636ed..cb6bbc6 100644
> --- a/kernel/sched.c
> +++ b/kernel/sched.c
> @@ -2613,28 +2613,35 @@ void sched_fork(struct task_struct *p, int clone_flags)
>  	set_task_cpu(p, cpu);
>  
>  	/*
> -	 * Revert to default priority/policy on fork if requested. Make sure we
> -	 * do not leak PI boosting priority to the child.
> +	 * Make sure we do not leak PI boosting priority to the child.
>  	 */
> -	if (current->sched_reset_on_fork &&
> -			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
> -		p->policy = SCHED_NORMAL;
> +	p->prio = current->normal_prio;
>  
> -	if (current->sched_reset_on_fork &&
> -			(current->normal_prio < DEFAULT_PRIO))
> -		p->prio = DEFAULT_PRIO;
> -	else
> -		p->prio = current->normal_prio;
> +	/*
> +	 * Revert to default priority/policy on fork if requested.
> +	 */
> +	if (unlikely(p->sched_reset_on_fork)) {
> +		if (p->policy == SCHED_FIFO || p->policy == SCHED_RR)
> +			p->policy = SCHED_NORMAL;
> +
> +		if (p->normal_prio < DEFAULT_PRIO)
> +			p->prio = DEFAULT_PRIO;
> +
> +		if (PRIO_TO_NICE(p->static_prio) < 0) {
> +			p->static_prio = NICE_TO_PRIO(0);
> +			set_load_weight(p);
> +		}
> +
> +		/*
> +		 * We don't need the reset flag anymore after the fork. It has
> +		 * fulfilled its duty:
> +		 */
> +		p->sched_reset_on_fork = 0;
> +	}
>  
>  	if (!rt_prio(p->prio))
>  		p->sched_class = &fair_sched_class;
>  
> -	/*
> -	 * We don't need the reset flag anymore after the fork. It has
> -	 * fulfilled its duty:
> -	 */
> -	p->sched_reset_on_fork = 0;
> -
>  #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
>  	if (likely(sched_info_on()))
>  		memset(&p->sched_info, 0, sizeof(p->sched_info));
> 


Lennart

-- 
Lennart Poettering                        Red Hat, Inc.
lennart [at] poettering [dot] net
http://0pointer.net/lennart/           GnuPG 0x1A015CC4

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

* [patch 1/2] Re: [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try
  2009-06-16 16:47   ` Lennart Poettering
@ 2009-06-17  8:46     ` Mike Galbraith
  2009-06-17  8:48       ` [patch 2/2] " Mike Galbraith
  2009-06-17 16:36       ` [tip:sched/core] sched: Clean up SCHED_RESET_ON_FORK tip-bot for Mike Galbraith
  0 siblings, 2 replies; 9+ messages in thread
From: Mike Galbraith @ 2009-06-17  8:46 UTC (permalink / raw)
  To: Lennart Poettering; +Cc: Peter Zijlstra, Ingo Molnar, linux-kernel

On Tue, 2009-06-16 at 18:47 +0200, Lennart Poettering wrote:
> On Tue, 16.06.09 11:05, Mike Galbraith (efault@gmx.de) wrote:
> 
> > I think it's cleaner to keep reset_on_fork functionality separate.
> > Thoughts on the below?
> 
> Looks good to me!

OK, I'll submit then, splitting cleanup from functionality addition.

commit 58e1710a8a525e0fb1f4c608d5f73377fb56c893
Author: Mike Galbraith <efault@gmx.de>
Date:   Wed Jun 17 10:16:26 2009 +0200

    sched: SCHED_RESET_ON_FORK cleanup.
    
    Make SCHED_RESET_ON_FORK sched_fork() bits a self-contained unlikely code path.
    
    Signed-off-by: Mike Galbraith <efault@gmx.de>
    Cc: Ingo Molnar <mingo@elte.hu>
    Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
    Cc: Lennart Poettering <mzxreary@0pointer.de>
    LKML-Reference: <new-submission>
---
 kernel/sched.c |   34 ++++++++++++++++++----------------
 1 files changed, 18 insertions(+), 16 deletions(-)

diff --git a/kernel/sched.c b/kernel/sched.c
index 095892c..3c27e44 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2613,28 +2613,30 @@ void sched_fork(struct task_struct *p, int clone_flags)
 	set_task_cpu(p, cpu);
 
 	/*
-	 * Revert to default priority/policy on fork if requested. Make sure we
-	 * do not leak PI boosting priority to the child.
+	 * Make sure we do not leak PI boosting priority to the child.
 	 */
-	if (current->sched_reset_on_fork &&
-			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
-		p->policy = SCHED_NORMAL;
+	p->prio = current->normal_prio;
 
-	if (current->sched_reset_on_fork &&
-			(current->normal_prio < DEFAULT_PRIO))
-		p->prio = DEFAULT_PRIO;
-	else
-		p->prio = current->normal_prio;
+	/*
+	 * Revert to default priority/policy on fork if requested.
+	 */
+	if (unlikely(p->sched_reset_on_fork)) {
+		if (p->policy == SCHED_FIFO || p->policy == SCHED_RR)
+			p->policy = SCHED_NORMAL;
+
+		if (p->normal_prio < DEFAULT_PRIO)
+			p->prio = DEFAULT_PRIO;
+
+		/*
+		 * We don't need the reset flag anymore after the fork. It has
+		 * fulfilled its duty:
+		 */
+		p->sched_reset_on_fork = 0;
+	}
 
 	if (!rt_prio(p->prio))
 		p->sched_class = &fair_sched_class;
 
-	/*
-	 * We don't need the reset flag anymore after the fork. It has
-	 * fulfilled its duty:
-	 */
-	p->sched_reset_on_fork = 0;
-
 #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
 	if (likely(sched_info_on()))
 		memset(&p->sched_info, 0, sizeof(p->sched_info));



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

* [patch 2/2] Re: [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try
  2009-06-17  8:46     ` [patch 1/2] " Mike Galbraith
@ 2009-06-17  8:48       ` Mike Galbraith
  2009-06-17 16:36         ` [tip:sched/core] sched: Add SCHED_RESET_ON_FORK functionality for nice < 0 tasks tip-bot for Mike Galbraith
  2009-06-17 16:36       ` [tip:sched/core] sched: Clean up SCHED_RESET_ON_FORK tip-bot for Mike Galbraith
  1 sibling, 1 reply; 9+ messages in thread
From: Mike Galbraith @ 2009-06-17  8:48 UTC (permalink / raw)
  To: Lennart Poettering; +Cc: Peter Zijlstra, Ingo Molnar, linux-kernel

commit 50f3ff67c7fbcd37f0a135113ecd56f724d9b081
Author: Mike Galbraith <efault@gmx.de>
Date:   Wed Jun 17 10:30:19 2009 +0200

    sched: Add SCHED_RESET_ON_FORK functionality for nice < 0 tasks.
    
    Signed-off-by: Mike Galbraith <efault@gmx.de>
    Cc: Ingo Molnar <mingo@elte.hu>
    Cc: Peter Zijlstra <a.p.zijlstra@chello.nl>
    Cc: Lennart Poettering <mzxreary@0pointer.de>
    LKML-Reference: <new-submission>
---
 kernel/sched.c |    5 +++++
 1 files changed, 5 insertions(+), 0 deletions(-)

diff --git a/kernel/sched.c b/kernel/sched.c
index 3c27e44..fe31c2d 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2627,6 +2627,11 @@ void sched_fork(struct task_struct *p, int clone_flags)
 		if (p->normal_prio < DEFAULT_PRIO)
 			p->prio = DEFAULT_PRIO;
 
+		if (PRIO_TO_NICE(p->static_prio) < 0) {
+			p->static_prio = NICE_TO_PRIO(0);
+			set_load_weight(p);
+		}
+
 		/*
 		 * We don't need the reset flag anymore after the fork. It has
 		 * fulfilled its duty:



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

* [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag, fix
  2009-06-16  9:05 ` [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Mike Galbraith
  2009-06-16 16:47   ` Lennart Poettering
@ 2009-06-17 10:32   ` tip-bot for Mike Galbraith
  1 sibling, 0 replies; 9+ messages in thread
From: tip-bot for Mike Galbraith @ 2009-06-17 10:32 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: linux-kernel, hpa, mingo, peterz, efault, lennart, tglx, mingo

Commit-ID:  e53438963eacc5624b61293f64e9f93c71f71198
Gitweb:     http://git.kernel.org/tip/e53438963eacc5624b61293f64e9f93c71f71198
Author:     Mike Galbraith <efault@gmx.de>
AuthorDate: Tue, 16 Jun 2009 11:05:08 +0200
Committer:  Ingo Molnar <mingo@elte.hu>
CommitDate: Wed, 17 Jun 2009 09:01:51 +0200

sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag, fix

Make SCHED_RESET_ON_FORK to DTRT for reniced tasks, and make the
sched_fork() SCHED_RESET_ON_FORK bits a self-contained unlikely
code block.

Signed-off-by: Mike Galbraith <efault@gmx.de>
Acked-by: Lennart Poettering <lennart@poettering.net>
Cc: Peter Zijlstra <peterz@infradead.org>
LKML-Reference: <1245143108.6038.10.camel@marge.simson.net>
Signed-off-by: Ingo Molnar <mingo@elte.hu>
 kernel/sched.c |   41 ++++++++++++++++++++++++-----------------
 1 file changed, 24 insertions(+), 17 deletions(-)


---
 kernel/sched.c |   39 +++++++++++++++++++++++----------------
 1 files changed, 23 insertions(+), 16 deletions(-)

diff --git a/kernel/sched.c b/kernel/sched.c
index 32e6ede..34f9424 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2613,28 +2613,35 @@ void sched_fork(struct task_struct *p, int clone_flags)
 	set_task_cpu(p, cpu);
 
 	/*
-	 * Revert to default priority/policy on fork if requested. Make sure we
-	 * do not leak PI boosting priority to the child.
+	 * Make sure we do not leak PI boosting priority to the child.
 	 */
-	if (current->sched_reset_on_fork &&
-			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
-		p->policy = SCHED_NORMAL;
+	p->prio = current->normal_prio;
 
-	if (current->sched_reset_on_fork &&
-			(current->normal_prio < DEFAULT_PRIO))
-		p->prio = DEFAULT_PRIO;
-	else
-		p->prio = current->normal_prio;
+	/*
+	 * Revert to default priority/policy on fork if requested.
+	 */
+	if (unlikely(p->sched_reset_on_fork)) {
+		if (p->policy == SCHED_FIFO || p->policy == SCHED_RR)
+			p->policy = SCHED_NORMAL;
+
+		if (p->normal_prio < DEFAULT_PRIO)
+			p->prio = DEFAULT_PRIO;
+
+		if (PRIO_TO_NICE(p->static_prio) < 0) {
+			p->static_prio = NICE_TO_PRIO(0);
+			set_load_weight(p);
+		}
+
+		/*
+		 * We don't need the reset flag anymore after the fork. It has
+		 * fulfilled its duty:
+		 */
+		p->sched_reset_on_fork = 0;
+	}
 
 	if (!rt_prio(p->prio))
 		p->sched_class = &fair_sched_class;
 
-	/*
-	 * We don't need the reset flag anymore after the fork. It has
-	 * fulfilled its duty:
-	 */
-	p->sched_reset_on_fork = 0;
-
 #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
 	if (likely(sched_info_on()))
 		memset(&p->sched_info, 0, sizeof(p->sched_info));

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

* [tip:sched/core] sched: Clean up SCHED_RESET_ON_FORK
  2009-06-17  8:46     ` [patch 1/2] " Mike Galbraith
  2009-06-17  8:48       ` [patch 2/2] " Mike Galbraith
@ 2009-06-17 16:36       ` tip-bot for Mike Galbraith
  1 sibling, 0 replies; 9+ messages in thread
From: tip-bot for Mike Galbraith @ 2009-06-17 16:36 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: linux-kernel, hpa, mingo, peterz, efault, mzxreary, tglx, mingo

Commit-ID:  b9dc29e72fd3dc2a739ce8eafd958220d0745734
Gitweb:     http://git.kernel.org/tip/b9dc29e72fd3dc2a739ce8eafd958220d0745734
Author:     Mike Galbraith <efault@gmx.de>
AuthorDate: Wed, 17 Jun 2009 10:46:01 +0200
Committer:  Ingo Molnar <mingo@elte.hu>
CommitDate: Wed, 17 Jun 2009 18:34:17 +0200

sched: Clean up SCHED_RESET_ON_FORK

Make SCHED_RESET_ON_FORK sched_fork() bits a self-contained unlikely code path.

Signed-off-by: Mike Galbraith <efault@gmx.de>
Acked-by: Lennart Poettering <mzxreary@0pointer.de>
Cc: Peter Zijlstra <peterz@infradead.org>
LKML-Reference: <1245228361.18329.6.camel@marge.simson.net>
Signed-off-by: Ingo Molnar <mingo@elte.hu>


---
 kernel/sched.c |   34 ++++++++++++++++++----------------
 1 files changed, 18 insertions(+), 16 deletions(-)

diff --git a/kernel/sched.c b/kernel/sched.c
index 32e6ede..50e4e3d 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2613,28 +2613,30 @@ void sched_fork(struct task_struct *p, int clone_flags)
 	set_task_cpu(p, cpu);
 
 	/*
-	 * Revert to default priority/policy on fork if requested. Make sure we
-	 * do not leak PI boosting priority to the child.
+	 * Make sure we do not leak PI boosting priority to the child.
 	 */
-	if (current->sched_reset_on_fork &&
-			(p->policy == SCHED_FIFO || p->policy == SCHED_RR))
-		p->policy = SCHED_NORMAL;
+	p->prio = current->normal_prio;
 
-	if (current->sched_reset_on_fork &&
-			(current->normal_prio < DEFAULT_PRIO))
-		p->prio = DEFAULT_PRIO;
-	else
-		p->prio = current->normal_prio;
+	/*
+	 * Revert to default priority/policy on fork if requested.
+	 */
+	if (unlikely(p->sched_reset_on_fork)) {
+		if (p->policy == SCHED_FIFO || p->policy == SCHED_RR)
+			p->policy = SCHED_NORMAL;
+
+		if (p->normal_prio < DEFAULT_PRIO)
+			p->prio = DEFAULT_PRIO;
+
+		/*
+		 * We don't need the reset flag anymore after the fork. It has
+		 * fulfilled its duty:
+		 */
+		p->sched_reset_on_fork = 0;
+	}
 
 	if (!rt_prio(p->prio))
 		p->sched_class = &fair_sched_class;
 
-	/*
-	 * We don't need the reset flag anymore after the fork. It has
-	 * fulfilled its duty:
-	 */
-	p->sched_reset_on_fork = 0;
-
 #if defined(CONFIG_SCHEDSTATS) || defined(CONFIG_TASK_DELAY_ACCT)
 	if (likely(sched_info_on()))
 		memset(&p->sched_info, 0, sizeof(p->sched_info));

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

* [tip:sched/core] sched: Add SCHED_RESET_ON_FORK functionality for nice < 0 tasks
  2009-06-17  8:48       ` [patch 2/2] " Mike Galbraith
@ 2009-06-17 16:36         ` tip-bot for Mike Galbraith
  0 siblings, 0 replies; 9+ messages in thread
From: tip-bot for Mike Galbraith @ 2009-06-17 16:36 UTC (permalink / raw)
  To: linux-tip-commits
  Cc: linux-kernel, hpa, mingo, peterz, efault, mzxreary, tglx, mingo

Commit-ID:  6c697bdf08a09ce461e305a22362973036e95db3
Gitweb:     http://git.kernel.org/tip/6c697bdf08a09ce461e305a22362973036e95db3
Author:     Mike Galbraith <efault@gmx.de>
AuthorDate: Wed, 17 Jun 2009 10:48:02 +0200
Committer:  Ingo Molnar <mingo@elte.hu>
CommitDate: Wed, 17 Jun 2009 18:34:18 +0200

sched: Add SCHED_RESET_ON_FORK functionality for nice < 0 tasks

Signed-off-by: Mike Galbraith <efault@gmx.de>
Acked-by: Lennart Poettering <mzxreary@0pointer.de>
Cc: Peter Zijlstra <peterz@infradead.org>
LKML-Reference: <1245228482.27326.1.camel@marge.simson.net>
Signed-off-by: Ingo Molnar <mingo@elte.hu>


---
 kernel/sched.c |    5 +++++
 1 files changed, 5 insertions(+), 0 deletions(-)

diff --git a/kernel/sched.c b/kernel/sched.c
index 50e4e3d..34f9424 100644
--- a/kernel/sched.c
+++ b/kernel/sched.c
@@ -2627,6 +2627,11 @@ void sched_fork(struct task_struct *p, int clone_flags)
 		if (p->normal_prio < DEFAULT_PRIO)
 			p->prio = DEFAULT_PRIO;
 
+		if (PRIO_TO_NICE(p->static_prio) < 0) {
+			p->static_prio = NICE_TO_PRIO(0);
+			set_load_weight(p);
+		}
+
 		/*
 		 * We don't need the reset flag anymore after the fork. It has
 		 * fulfilled its duty:

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

end of thread, other threads:[~2009-06-17 16:37 UTC | newest]

Thread overview: 9+ messages (download: mbox.gz follow: Atom feed
-- links below jump to the message on this page --
2009-06-15 15:27 [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Lennart Poettering
2009-06-15 15:37 ` [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag tip-bot for Lennart Poettering
2009-06-16  9:05 ` [PATCH] scheduler: introduce SCHED_RESET_ON_FORK scheduling policy flag, fourth try Mike Galbraith
2009-06-16 16:47   ` Lennart Poettering
2009-06-17  8:46     ` [patch 1/2] " Mike Galbraith
2009-06-17  8:48       ` [patch 2/2] " Mike Galbraith
2009-06-17 16:36         ` [tip:sched/core] sched: Add SCHED_RESET_ON_FORK functionality for nice < 0 tasks tip-bot for Mike Galbraith
2009-06-17 16:36       ` [tip:sched/core] sched: Clean up SCHED_RESET_ON_FORK tip-bot for Mike Galbraith
2009-06-17 10:32   ` [tip:sched/core] sched: Introduce SCHED_RESET_ON_FORK scheduling policy flag, fix tip-bot for Mike Galbraith

This is a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox