autogroup: sched_setscheduler() fails
Hi,
With autogroup ON, sched_setscheduler() fails when I try to change the scheduling policy of a normal task to either RR or FIFO.
sched_setscheduler() returns -EPERM when it finds that the group doesn't have any rt bandwidth. This is expected because with autogroup, the task is in an autogroup for which task_group(p)->rt_bandwidth.rt_runtime is 0.
I guess the task needs to be moved to appropriate cgroup (from its current autogroup) when such policy change is requested, but I wasn't sure if group change from sched_setscheduler() can be achieved easily.
Regards,
Bharata.
Quoted 5 lines · Bharata B Rao
Hi,
With autogroup ON,
sched_setscheduler()fails when I try to change the scheduling policy of a normal task to either RR or FIFO.
Quoted 7 lines
sched_setscheduler()returns-EPERMwhen it finds that the group doesn't have any rt bandwidth. This is expected because with autogroup, the task is in an autogroup for which task_group(p)->rt_bandwidth.rt_runtime is 0.I guess the task needs to be moved to appropriate cgroup (from its current autogroup) when such policy change is requested, but I wasn't sure if group change from
sched_setscheduler()can be achieved easily.
Right, autogroup should be excluding CONFIG_RT_GROUP_SCHED, since it doesn't currently support it.
sched: SCHED_AUTOGROUP selection excludes RT_GROUP_SCHED
Autogroup does not support realtime task groups, so make selection of SCHED_AUTOGROUP exclude RT_GROUP_SCHED.
--- init/Kconfig | 5 +++++ 1 file changed, 5 insertions(+)
init/Kconfig +5 -0
@@ -699,6 +699,7 @@ config RT_GROUP_SCHED bool "Group scheduling for SCHED_RR/FIFO" depends on EXPERIMENTAL depends on CGROUP_SCHED + depends on !SCHED_AUTOGROUP default n help This feature lets you explicitly allocate real CPU bandwidth
@@ -807,6 +808,10 @@ config SCHED_AUTOGROUP desktop applications. Task group autogeneration is currently based upon task session. + Note: SCHED_AUTOGROUP does not support realtime tasks, and prevents + enabling RT_GROUP_SCHED. If you intend to use group scheduling for + realtime tasks, do not enable this option. + config MM_OWNER bool
Quoted 29 lines · Mike Galbraith
Right, autogroup should be excluding
CONFIG_RT_GROUP_SCHED, since it doesn't currently support it.sched:
SCHED_AUTOGROUPselection excludesRT_GROUP_SCHEDAutogroup does not support realtime task groups, so make selection of
SCHED_AUTOGROUPexcludeRT_GROUP_SCHED.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>--- init/Kconfig | 5 +++++ 1 file changed, 5 insertions(+)Index: linux-2.6/init/Kconfig
===================================================================init/Kconfig +1
-0@@ -699,6 +699,7 @@ config RT_GROUP_SCHED bool "Group scheduling for SCHED_RR/FIFO" depends on EXPERIMENTAL depends on CGROUP_SCHED + depends on !SCHED_AUTOGROUP default n help This feature lets you explicitly allocate real CPU bandwidth
init/Kconfig config SCHED_AUTOGROUP · line 817
Quoted 10 lines
init/Kconfig +4
-0@@ -807,6 +808,10 @@ config SCHED_AUTOGROUP desktop applications. Task group autogeneration is currently based upon task session. + Note: SCHED_AUTOGROUP does not support realtime tasks, and prevents + enabling RT_GROUP_SCHED. If you intend to use group scheduling for + realtime tasks, do not enable this option. + config MM_OWNER bool
Uhm, no. The right way is to put tasks back into the root group and then perform sched_setscheduler().
Quoted 8 lines · Peter Zijlstra
Quoted 4 lines · Mike Galbraith
Autogroup does not support realtime task groups, so make selection of
SCHED_AUTOGROUPexcludeRT_GROUP_SCHED.Uhm, no. The right way is to put tasks back into the root group and then perform
sched_setscheduler().
I think that would take more lines, this look like a right way too?
sched, autogroup: move tasks to the appropriate runqueue on policy change.
If CONFIG_RT_GROUP_SCHED is set, sched_setscheduler() fails due to autogroup not allocating rt_runtime. Fool __sched_setscheduler() into proceeding on, and move tasks to the appropriate runqueue upon policy change.
--- kernel/sched.c | 9 ++++++--- kernel/sched_autogroup.c | 18 ++++++++++++++++++ kernel/sched_autogroup.h | 1 + 3 files changed, 25 insertions(+), 3 deletions(-)
kernel/sched.c +6 -3
@@ -4571,6 +4571,8 @@ void rt_mutex_setprio(struct task_struct p->prio = prio; +autogroup_setscheduler (p, on_rq); +if (running) p->sched_class->set_curr_task (rq);if (on_rq) {
@@ -4738,7 +4740,7 @@ static struct task_struct *find_process_/* Actually do priority change: must hold rq lock. */ static void -__setscheduler (struct rq *rq,struct task_struct *p,int policy,int prio) +__setscheduler (struct rq *rq,struct task_struct *p,int policy,int prio,int on_rq) {BUG_ON (p->se.on_rq);
@@ -4752,6 +4754,7 @@ __setscheduler(struct rq *rq, struct taselse p->sched_class = &fair_sched_class;set_load_weight (p); +autogroup_setscheduler (p, on_rq); }/*
@@ -4900,7 +4903,7 @@ recheck: oldprio = p->prio; prev_class = p->sched_class; -__setscheduler (rq, p, policy, param->sched_priority); +__setscheduler (rq, p, policy, param->sched_priority, on_rq);if (running) p->sched_class->set_curr_task (rq);
@@ -8116,7 +8119,7 @@ static void normalize_task(struct rq *rq on_rq = p->se.on_rq;if (on_rq)deactivate_task (rq, p,0 ); -__setscheduler (rq, p,SCHED_NORMAL ,0 ); +__setscheduler (rq, p,SCHED_NORMAL ,0 , on_rq);if (on_rq) {activate_task (rq, p,0 );resched_task (rq->curr);
kernel/sched_autogroup.c +18 -0
@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;
@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); } +static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +/* Allocates GFP_KERNEL, cannot be called under any spinlock */ void sched_autogroup_create_attach (struct task_struct *p) {
kernel/sched_autogroup.h +1 -0
@@ -15,6 +15,7 @@ autogroup_task_group(struct task_structstatic inline void autogroup_init (struct task_struct *init_task) { }static inline void autogroup_free (struct task_group *tg) { } +static inline void autogroup_setscheduler (struct task_struct *p,int on_rq) { }static inline struct task_group *autogroup_task_group (struct task_struct *p,struct task_group *tg)
Quoted 23 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }
kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 163
Quoted 10 lines
kernel/sched_autogroup.c +9
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +
IIUC, with the above changes you are actually queing the task into rt_rq of an autogroup. But the task's autogroup interface (/proc/<pid>/autogroup) allows you to control the bandwidth of only cfs_rq tasks, while the rt tasks in the group get RUNTIME_INF bandwidth.
I think what we need is a real group change here (which is difficult I think) and not just sched_class change.
Regards,
Bharata.
Quoted 40 lines · Bharata B Rao
Quoted 23 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 163
Quoted 10 lines
kernel/sched_autogroup.c +9
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +IIUC, with the above changes you are actually queing the task into
rt_rqof an autogroup. But the task's autogroup interface (/proc/<pid>/autogroup) allows you to control the bandwidth of onlycfs_rqtasks, while the rt tasks in the group getRUNTIME_INFbandwidth.
Quoted 2 lines
I think what we need is a real group change here (which is difficult I think) and not just
sched_classchange.
Unless I fscked up, set_task_rq() is the group change. As soon as the task's class changes, it'll be moved to the root_task_group.
-Mike
Quoted 41 lines · Mike Galbraith
Quoted 40 lines · Bharata B Rao
Quoted 23 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 163
Quoted 10 lines
kernel/sched_autogroup.c +9
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +IIUC, with the above changes you are actually queing the task into
rt_rqof an autogroup. But the task's autogroup interface (/proc/<pid>/autogroup) allows you to control the bandwidth of onlycfs_rqtasks, while the rt tasks in the group getRUNTIME_INFbandwidth.
Quoted 5 lines
Quoted 2 lines
I think what we need is a real group change here (which is difficult I think) and not just
sched_classchange.Unless I fscked up,
set_task_rq()is the group change. As soon as the task's class changes, it'll be moved to theroot_task_group.
Ok, this is what I understand, may be Peter Z can confirm...
set_task_rq() just changes the task's cfs_rq and rt_rq as per its task_group(). The normal way to change a task's group is to first change its cgroup pointer (task->cgroups, see cgroup_attach_task()) After this you change the runqueues by calling set_task_rq() which now refers to new group's runqueues.
In your code, I don't see where you really change task's group. AFAICS, it continues to remain in the same autogroup.
Regards,
Bharata.
Quoted 5 lines · Bharata B Rao
Quoted 2 lines
Unless I fscked up,
set_task_rq()is the group change. As soon as the task's class changes, it'll be moved to theroot_task_group.Ok, this is what I understand, may be Peter Z can confirm...
Quoted 8 lines
set_task_rq()just changes the task'scfs_rqandrt_rqas per itstask_group(). The normal way to change a task's group is to first change its cgroup pointer (task->cgroups, seecgroup_attach_task()) After this you change the runqueues by callingset_task_rq()which now refers to new group's runqueues.In your code, I don't see where you really change task's group. AFAICS, it continues to remain in the same autogroup.
IMHO, task->cgroups will not change when autogroup take effect. IOW, autogroup will only take effect when task belongs to root_task_group.
Thanks,
Yong
Quoted 9 lines
Regards,
Bharata.
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to [email protected]
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Signature · 1 line
Only stand for myself
Quoted 13 lines · Yong Zhang
Quoted 11 lines · Bharata B Rao
Quoted 2 lines
Unless I fscked up,
set_task_rq()is the group change. As soon as the task's class changes, it'll be moved to theroot_task_group.Ok, this is what I understand, may be Peter Z can confirm...
set_task_rq()just changes the task'scfs_rqandrt_rqas per itstask_group(). The normal way to change a task's group is to first change its cgroup pointer (task->cgroups, seecgroup_attach_task()) After this you change the runqueues by callingset_task_rq()which now refers to new group's runqueues.
Quoted 4 lines
Quoted 2 lines
In your code, I don't see where you really change task's group. AFAICS, it continues to remain in the same autogroup.
IMHO,
task->cgroupswill not change when autogroup take effect.
Yes and I believe this is cause for some of the weird semantics I see with autogroup and cgroups. I am not sure if this has already been discussed ealier, may be I need to go back and check the archives, but consider this:
I have cpu cgroup mounted at /cgroup and see that all the tasks in the system are listed in /cgroup/tasks file.
Now I start a task like this:
# ./while1 & [1] 2761
and see that this task belongs to root cgroup.
# grep 2761 /cgroup/tasks 2671
But we know that this task really belongs to an autogroup and is not sitting directly on root_task_group.
# cat /proc/2761/autogroup /autogroup-49 nice 0
So we have a task in an autogroup (which is a sub group of root_task_group) but is being shown as part of root_task_group. Is this by design ?
Now say I create a sub cgroup and move this task to it.
# mkdir /cgroup/1 # echo 2671 > /cgroup/1/tasks
So now the task moved to a real cgroup.
# cat /cgroup/1/tasks 2761
But the /proc/2761/autogroup isn't updated. It still shows /autogroup-49 nice 0
May be this was all discussed earlier as I noted in the beginning, but I find this semantics a bit unusual.
Regards,
Bharata.
Quoted 12 lines · Bharata B Rao
Quoted 1 line · Yong Zhang
IMHO,
task->cgroupswill not change when autogroup take effect.Yes and I believe this is cause for some of the weird semantics I see with autogroup and cgroups. I am not sure if this has already been discussed ealier, may be I need to go back and check the archives, but consider this:
I have cpu cgroup mounted at /cgroup and see that all the tasks in the system are listed in /cgroup/tasks file.
Quoted 6 lines
Now I start a task like this:
# ./while1 & [1] 2761and see that this task belongs to root cgroup.
Yes, cgroups sees cgroup associations, not autogroup associations.
Quoted 5 lines
# grep 2761 /cgroup/tasks 2671But we know that this task really belongs to an autogroup and is not sitting directly on
root_task_group.
Yup, cgroups doesn't want it, so autogroup (if enabled) claims it.
Quoted 5 lines
# cat /proc/2761/autogroup /autogroup-49 nice 0So we have a task in an autogroup (which is a sub group of
root_task_group) but is being shown as part ofroot_task_group. Is this by design ?
Yes, it's supposed to be transparent to cgroups.
Quoted 5 lines
Now say I create a sub cgroup and move this task to it.
# mkdir /cgroup/1 # echo 2671 > /cgroup/1/tasks
Quoted 7 lines
So now the task moved to a real cgroup.
# cat /cgroup/1/tasks 2761But the
/proc/2761/autogroupisn't updated. It still shows /autogroup-49 nice 0
The proc interface shows task->autogroup associations, which always exist. This is autogroups' view of the world, just as cgroup/tasks is cgroups' view of it's world.
Quoted 2 lines
May be this was all discussed earlier as I noted in the beginning, but I find this semantics a bit unusual.
Makes perfect sense to me.
-Mike
Quoted 30 lines · Mike Galbraith
Quoted 12 lines · Bharata B Rao
Quoted 1 line · Yong Zhang
IMHO,
task->cgroupswill not change when autogroup take effect.Yes and I believe this is cause for some of the weird semantics I see with autogroup and cgroups. I am not sure if this has already been discussed ealier, may be I need to go back and check the archives, but consider this:
I have cpu cgroup mounted at /cgroup and see that all the tasks in the system are listed in /cgroup/tasks file.
Quoted 6 lines
Now I start a task like this:
# ./while1 & [1] 2761and see that this task belongs to root cgroup.
Yes, cgroups sees cgroup associations, not autogroup associations.
Quoted 5 lines
# grep 2761 /cgroup/tasks 2671But we know that this task really belongs to an autogroup and is not sitting directly on
root_task_group.Yup, cgroups doesn't want it, so autogroup (if enabled) claims it.
Quoted 7 lines
Quoted 5 lines
# cat /proc/2761/autogroup /autogroup-49 nice 0So we have a task in an autogroup (which is a sub group of
root_task_group) but is being shown as part ofroot_task_group. Is this by design ?Yes, it's supposed to be transparent to cgroups.
If cgroups doesn't want that task and if its transparent to cgroups, why is it shown as part of /cgroups/tasks ? The task really doesn't belong in there. Its not on the runqueue of root_task_group.
So basically I feel that a task consumed by autogroup shouldn't ideally be shown in root cgroup's tasks file.
Regards,
Bharata.
Quoted 4 lines · Bharata B Rao
Quoted 1 line · Mike Galbraith
Yes, it's supposed to be transparent to cgroups.
Quoted 8 lines
If cgroups doesn't want that task and if its transparent to cgroups, why is it shown as part of /cgroups/tasks ? The task really doesn't belong in there. Its not on the runqueue of
root_task_group.So basically I feel that a task consumed by autogroup shouldn't ideally be shown in root cgroup's tasks file.
From cgroups' viewpoint, root is where it's at. The task isn't consumed
by autogroup either, it's only borrowed until cgroups claims it.
Would you prefer that when you mount /cgroups, you see a nearly empty root task list because box was booted with autogroup enabled? Should tasks appear and disappear on the fly while you're watching?
The goal is peaceful coexistence. The user can turn either or both both on/off at his/her whim.
-Mike
Quoted 9 lines · Mike Galbraith
Quoted 8 lines · Bharata B Rao
Quoted 1 line · Mike Galbraith
Yes, it's supposed to be transparent to cgroups.
If cgroups doesn't want that task and if its transparent to cgroups, why is it shown as part of /cgroups/tasks ? The task really doesn't belong in there. Its not on the runqueue of
root_task_group.
Quoted 8 lines
Quoted 4 lines
So basically I feel that a task consumed by autogroup shouldn't ideally be shown in root cgroup's tasks file.
From cgroups' viewpoint, root is where it's at. The task isn't consumed
by autogroup either, it's only borrowed until cgroups claims it.
Would you prefer that when you mount /cgroups, you see a nearly empty root task list because box was booted with autogroup enabled?
If I had my way, I would say yes :) I would even say make autogroups visible so that we know exactly what it is. Let 'auto' in autogroups mean only 'automatic' and not necessarily 'hidden'.
Quoted 2 lines
Should
tasks appear and disappear on the fly while you're watching?
Why would they unless we explicitly move them ?
Anyway I guess you would have gone through these questions already. Thanks for patiently answering :)
Regards,
Bharata.
Quoted 45 lines · Bharata B Rao
Quoted 44 lines · Mike Galbraith
Quoted 42 lines · Bharata B Rao
Quoted 23 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 163
Quoted 10 lines
kernel/sched_autogroup.c +9
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +IIUC, with the above changes you are actually queing the task into
rt_rqof an autogroup. But the task's autogroup interface (/proc/<pid>/autogroup) allows you to control the bandwidth of onlycfs_rqtasks, while the rt tasks in the group getRUNTIME_INFbandwidth.I think what we need is a real group change here (which is difficult I think) and not just
sched_classchange.
Quoted 7 lines
Quoted 2 lines
Unless I fscked up,
set_task_rq()is the group change. As soon as the task's class changes, it'll be moved to theroot_task_group.Ok, this is what I understand, may be Peter Z can confirm...
set_task_rq()just changes the task'scfs_rqandrt_rqas per itstask_group().
Exactly. When you call task_group() for an RT task, it returns &root_task_group, so a task making the transition to RT will be dequeued from it's autogroup cfs_rq, and enqueued in root_task_group's rt_rq.
Quoted 4 lines
The normal way to change a task's group is to first
change its cgroup pointer (task->cgroups, seecgroup_attach_task()) After this you change the runqueues by callingset_task_rq()which now refers to new group's runqueues.
Autogroup doesn't need to do cgroup stuff. If a task is in a cgroup, it's autogroup remains intact, but is ignored. Move it back to root, and it's autogroup will be used again.
-Mike
Quoted 49 lines · Mike Galbraith
Quoted 48 lines · Bharata B Rao
Quoted 46 lines · Mike Galbraith
Quoted 40 lines · Bharata B Rao
Quoted 23 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 163
Quoted 10 lines
kernel/sched_autogroup.c +9
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +IIUC, with the above changes you are actually queing the task into
rt_rqof an autogroup. But the task's autogroup interface (/proc/<pid>/autogroup) allows you to control the bandwidth of onlycfs_rqtasks, while the rt tasks in the group getRUNTIME_INFbandwidth.Quoted 2 lines
I think what we need is a real group change here (which is difficult I think) and not just
sched_classchange.Unless I fscked up,
set_task_rq()is the group change. As soon as the task's class changes, it'll be moved to theroot_task_group.
Quoted 8 lines
Quoted 4 lines
Ok, this is what I understand, may be Peter Z can confirm...
set_task_rq()just changes the task'scfs_rqandrt_rqas per itstask_group().Exactly. When you call
task_group()for an RT task, it returns&root_task_group, so a task making the transition to RT will be dequeued from it's autogroupcfs_rq, and enqueued in root_task_group'srt_rq.
Oh yes, forgot that addition to task_group() for a moment!
Regards,
Bharata.
Quoted 41 lines · Mike Galbraith
Quoted 40 lines · Bharata B Rao
Quoted 23 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 163
Quoted 10 lines
kernel/sched_autogroup.c +9
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq); +else +set_task_rq (p,task_cpu (p)); +} +IIUC, with the above changes you are actually queing the task into
rt_rqof an autogroup. But the task's autogroup interface (/proc/<pid>/autogroup) allows you to control the bandwidth of onlycfs_rqtasks, while the rt tasks in the group getRUNTIME_INFbandwidth.
Quoted 5 lines
Quoted 2 lines
I think what we need is a real group change here (which is difficult I think) and not just
sched_classchange.Unless I fscked up,
set_task_rq()is the group change. As soon as the task's class changes, it'll be moved to theroot_task_group.
But it'd be better to not touch anything, just deflect RT tasks away from useless queues from the start.
sched, autogroup: fix CONFIG_RT_GROUP_SCHED sched_setscheduler() failure.
If CONFIG_RT_GROUP_SCHED is set, sched_setscheduler() fails due to autogroup not allocating rt_runtime. Squirrel allocated but useless rt_se and rt_rq away for group destruction time, and deflect RT tasks to the root task group.
--- kernel/sched_autogroup.c | 13 +++++++++++++ kernel/sched_autogroup.h | 4 ++++ 2 files changed, 17 insertions(+)
kernel/sched_autogroup.c +13 -0
@@ -27,6 +27,11 @@ static inline void autogroup_destroy(str { struct autogroup *ag = container_of(kref, struct autogroup, kref); +#ifdef CONFIG_RT_GROUP_SCHED + ag->tg->rt_se = ag->rt_se; + ag->tg->rt_rq = ag->rt_rq; + ag->tg->rt_bandwidth.rt_runtime =0 ; +#endif sched_destroy_group (ag->tg); }
@@ -72,6 +77,14 @@ static inline struct autogroup *autogrouinit_rwsem (&ag->lock); ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; +#ifdef CONFIG_RT_GROUP_SCHED +/* Sorry, we don't do RT, go away. */ + ag->rt_se = tg->rt_se; + ag->rt_rq = tg->rt_rq; + tg->rt_se = root_task_group.rt_se; + tg->rt_rq = root_task_group.rt_rq; + tg->rt_bandwidth.rt_runtime = root_task_group.rt_bandwidth.rt_runtime; +#endif tg->autogroup = ag;return ag;
kernel/sched_autogroup.h +4 -0
@@ -6,6 +6,10 @@ struct autogroup {struct rw_semaphore lock;unsigned long id;int nice; +#ifdef CONFIG_RT_GROUP_SCHED +struct sched_rt_entity **rt_se; +struct rt_rq **rt_rq; +#endif }; static inline struct task_group *
Quoted 34 lines · Mike Galbraith
But it'd be better to not touch anything, just deflect RT tasks away from useless queues from the start.
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Squirrel allocated but uselessrt_seandrt_rqaway for group destruction time, and deflect RT tasks to the root task group.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>---
kernel/sched_autogroup.c | 13 +++++++++++++
kernel/sched_autogroup.h | 4 ++++2 files changed, 17 insertions(+)Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +5
-0@@ -27,6 +27,11 @@ static inline void autogroup_destroy(str { struct autogroup *ag = container_of(kref, struct autogroup, kref); +#ifdef CONFIG_RT_GROUP_SCHED + ag->tg->rt_se = ag->rt_se; + ag->tg->rt_rq = ag->rt_rq; + ag->tg->rt_bandwidth.rt_runtime = 0; +#endif sched_destroy_group(ag->tg); }
kernel/sched_autogroup.c static inline struct autogroup *autogrou · line 86
Quoted 10 lines
kernel/sched_autogroup.c +7
-0@@ -72,6 +77,14 @@ static inline struct autogroup *autogrou init_rwsem(&ag->lock); ag->id = atomic_inc_return(&autogroup_seq_nr); ag->tg = tg; +#ifdef CONFIG_RT_GROUP_SCHED + /* Sorry, we don't do RT, go away. */ + ag->rt_se = tg->rt_se; + ag->rt_rq = tg->rt_rq; + tg->rt_se = root_task_group.rt_se; + tg->rt_rq = root_task_group.rt_rq; + tg->rt_bandwidth.rt_runtime = root_task_group.rt_bandwidth.rt_runtime;
Setting rt_runtime both in this patch and the previous one will make tune other's rt_runtime/rt_period trouble, I guess.
Thanks,
Yong
Signature · 1 line
Only stand for myself
Quoted 2 lines · Yong Zhang
Setting
rt_runtimeboth in this patch and the previous one will make tune other's rt_runtime/rt_period trouble, I guess.
Hrmph, how annoying. I'll take another look at rt_runtime.
-Mike
(mailer switched me to work account again. grrrr, switch yet again:)
Quoted 2 lines · Yong Zhang
Setting
rt_runtimeboth in this patch and the previous one will make tune other's rt_runtime/rt_period trouble, I guess.
Yeah, as in making it impossible to allocate even 1 usec :) We need zero bandwidth though, so tell __sched_setscheduler() that autogroups having zero allocated is perfectly fine.
sched, autogroup: fix CONFIG_RT_GROUP_SCHED sched_setscheduler() failure.
If CONFIG_RT_GROUP_SCHED is set, __sched_setscheduler() fails due to autogroup not allocating rt_runtime. Free unused/unusable rt_se and rt_rq, redirect RT tasks to the root task group, and tell __sched_setscheduler() that it's ok.
--- kernel/sched.c | 3 ++- kernel/sched_autogroup.c | 27 +++++++++++++++++++++++++++ kernel/sched_autogroup.h | 4 ++++ 3 files changed, 33 insertions(+), 1 deletion(-)
kernel/sched_autogroup.c +27 -0
@@ -27,6 +27,11 @@ static inline void autogroup_destroy(str { struct autogroup *ag = container_of(kref, struct autogroup, kref); +#ifdef CONFIG_RT_GROUP_SCHED +/* We've redirected RT tasks to the root task group... */ + ag->tg->rt_se =NULL ; + ag->tg->rt_rq =NULL ; +#endif sched_destroy_group (ag->tg); }
@@ -55,6 +60,10 @@ static inline struct autogroup *autogroureturn ag; } +#ifdef CONFIG_RT_GROUP_SCHED +static void free_rt_sched_group (struct task_group *tg); +#endif +static inline struct autogroup *autogroup_create (void ) {struct autogroup *ag =kzalloc (sizeof (*ag),GFP_KERNEL );
@@ -72,6 +81,19 @@ static inline struct autogroup *autogrouinit_rwsem (&ag->lock); ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* Autogroup RT tasks are redirected to the root task group +* so we don't have to move tasks around upon policy change, +* or flail around trying to allocate bandwidth on the fly. +* A bandwidth exception in __sched_setscheduler() allows +* the policy change to proceed. Thereafter, task_group() +* returns &root_task_group, so zero bandwidth is required. +*/ +free_rt_sched_group (tg); + tg->rt_se = root_task_group.rt_se; + tg->rt_rq = root_task_group.rt_rq; +#endif tg->autogroup = ag;return ag;
@@ -106,6 +128,11 @@ task_wants_autogroup(struct task_structreturn true; } +static inline bool task_group_is_autogroup (struct task_group *tg) +{ +return tg != &root_task_group && tg->autogroup; +} +static inline struct task_group *autogroup_task_group (struct task_struct *p,struct task_group *tg) {
kernel/sched_autogroup.h +4 -0
@@ -15,6 +15,10 @@ autogroup_task_group(struct task_structstatic inline void autogroup_init (struct task_struct *init_task) { }static inline void autogroup_free (struct task_group *tg) { } +static inline bool task_group_is_autogroup (struct task_group *tg) +{ +return 0 ; +}static inline struct task_group *autogroup_task_group (struct task_struct *p,struct task_group *tg)
kernel/sched.c +2 -1
@@ -4874,7 +4874,8 @@ recheck:* assigned. */ if (rt_bandwidth_enabled () &&rt_policy (policy) && -task_group (p)->rt_bandwidth.rt_runtime ==0 ) { +task_group (p)->rt_bandwidth.rt_runtime ==0 && + !task_group_is_autogroup (task_group (p))) {__task_rq_unlock (rq);raw_spin_unlock_irqrestore (&p->pi_lock, flags);return -EPERM ;
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>
This looks more clear ;)
And a little comment below
kernel/sched_autogroup.c task_wants_autogroup(struct task_struct · line 133
Quoted 13 lines
---
kernel/sched.c | 3 ++-kernel/sched_autogroup.c| 27 +++++++++++++++++++++++++++kernel/sched_autogroup.h| 4 ++++3 files changed, 33 insertions(+), 1 deletion(-)kernel/sched_autogroup.c +3
-0@@ -106,6 +128,11 @@ task_wants_autogroup(struct task_struct return true; } +static inline bool task_group_is_autogroup (struct task_group *tg) +{ + return tg != &root_task_group && tg->autogroup;
Isn't just checking tg->autogroup sufficient?
if tg == &root_task_group
Quoted 8 lines
kernel/sched.c +0
-0@@ -4874,7 +4874,8 @@ recheck:* assigned. */ if (
rt_bandwidth_enabled()&&rt_policy(policy)&&
- task_group(p)->rt_bandwidth.rt_runtime == 0) {
+ task_group(p)->rt_bandwidth.rt_runtime == 0 &&
this check will fail.
Thanks,
Yong
Signature · 1 line
Only stand for myself
Quoted 24 lines · Yong Zhang
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>This looks more clear ;)
And a little comment below
Quoted 10 lines
---
kernel/sched.c | 3 ++-kernel/sched_autogroup.c| 27 +++++++++++++++++++++++++++kernel/sched_autogroup.h| 4 ++++3 files changed, 33 insertions(+), 1 deletion(-)kernel/sched_autogroup.c +0
-0@@ -106,6 +128,11 @@ task_wants_autogroup(struct task_struct return true; }
Quoted 5 lines
kernel/sched_autogroup.c task_wants_autogroup(struct task_struct · line 133
Quoted 3 lines
kernel/sched_autogroup.c +3
-0+static inline bool task_group_is_autogroup (struct task_group *tg) +{ + return tg != &root_task_group && tg->autogroup;Isn't just checking
tg->autogroupsufficient?
But if task_group_is_autogroup() will be called in other place in the future, checking (tg != &root_task_group) is needed.
Quoted 20 lines
if tg ==
&root_task_groupQuoted 8 lines
kernel/sched.c +0
-0@@ -4874,7 +4874,8 @@ recheck:* assigned. */ if (
rt_bandwidth_enabled()&&rt_policy(policy)&&
- task_group(p)->rt_bandwidth.rt_runtime == 0) {
+ task_group(p)->rt_bandwidth.rt_runtime == 0 &&this check will fail.
Thanks,
Yong--
Only stand for myself
Signature · 1 line
Only stand for myself
Quoted 32 lines · Yong Zhang
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>This looks more clear ;)
And a little comment below
kernel/sched_autogroup.c task_wants_autogroup(struct task_struct · line 133
Quoted 13 lines
--- kernel/sched.c | 3 ++- kernel/sched_autogroup.c | 27 +++++++++++++++++++++++++++ kernel/sched_autogroup.h | 4 ++++ 3 files changed, 33 insertions(+), 1 deletion(-)kernel/sched_autogroup.c +3
-0@@ -106,6 +128,11 @@ task_wants_autogroup(struct task_structreturn true; } +static inline bool task_group_is_autogroup (struct task_group *tg) +{ +return tg != &root_task_group && tg->autogroup;Isn't just checking
tg->autogroupsufficient?if tg ==
&root_task_group
Quoted 10 lines
kernel/sched.c recheck: · line 4877
Quoted 8 lines
kernel/sched.c +1
-1@@ -4874,7 +4874,8 @@ recheck:* assigned. */ if (rt_bandwidth_enabled() && rt_policy(policy) && -task_group (p)->rt_bandwidth.rt_runtime ==0 ) { + task_group(p)->rt_bandwidth.rt_runtime == 0 &&this check will fail.
Yes, it's intended to fail. I intend to make it explicit throughout autogroup that root_task_group is not an autogroup, and will drop the test for root_task_group then.
-Mike
Quoted 17 lines · Mike Galbraith
(mailer switched me to work account again. grrrr, switch yet again:)
Quoted 2 lines · Yong Zhang
Setting
rt_runtimeboth in this patch and the previous one will make tune other's rt_runtime/rt_period trouble, I guess.Yeah, as in making it impossible to allocate even 1 usec :) We need zero bandwidth though, so tell
__sched_setscheduler()that autogroups having zero allocated is perfectly fine.sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.
Quoted 9 lines
Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>--- kernel/sched.c | 3 ++- kernel/sched_autogroup.c | 27 +++++++++++++++++++++++++++ kernel/sched_autogroup.h | 4 ++++ 3 files changed, 33 insertions(+), 1 deletion(-)
Works fine here.
Thanks,
Bharata.
Peter Zijlstra
AppliedQuoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>
Thanks, applied!
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.
why isnt rt_runtime_us residing in a separate (new) subsystem ?
Signature · 1 line
torben Hohn
Quoted 11 lines · torbenh
Quoted 10 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>
Quoted 6 lines
Quoted 1 line
Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.
You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
Quoted 1 line
why isnt
rt_runtime_usresiding in a separate (new) subsystem ?
The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
-Mike
Quoted 14 lines · Mike Galbraith
Quoted 13 lines · torbenh
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
Quoted 7 lines
Quoted 4 lines
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
but i can not get the same behaviour as if CONFIG_RT_GROUP_SCHED was off. iE N cgroups with different cpu.share values, but each with rt_runtime_us=950000
if the rt_runtime_us was in a different subsystem, its my understanding that i could leave rt_runtime_us alone, and have all tasks in the root group in the rt_runtime subsystem.
Quoted 5 lines
Quoted 2 lines
why isnt
rt_runtime_usresiding in a separate (new) subsystem ?The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
sure it belongs to the user. but what if user wants to have different cpu.shares, but full rt_runtime_us for all tasks ?
i can not have 2 sibling cgroups, whose rt_runtime_us adds up to over the rt_period ...
Quoted 8 lines
-Mike
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to [email protected]
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Signature · 1 line
torben Hohn
Quoted 20 lines · torbenh
Quoted 19 lines · Mike Galbraith
Quoted 17 lines · torbenh
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.
Quoted 6 lines
Quoted 2 lines
You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
but i can not get the same behaviour as if
CONFIG_RT_GROUP_SCHEDwas off. iE N cgroups with different cpu.share values, but each with rt_runtime_us=950000
? if CONFIG_RT_GROUP_SCHED was a noop, it wouldn't exist.
Quoted 3 lines
if the
rt_runtime_uswas in a different subsystem, its my understanding that i could leavert_runtime_usalone, and have all tasks in the root group in thert_runtimesubsystem.
Sounds like you just want to turn CONFIG_RT_GROUP_SCHED off.
Quoted 5 lines
Quoted 2 lines
The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
sure it belongs to the user. but what if user wants to have different cpu.shares, but full
rt_runtime_usfor all tasks ?
Then the user doesn't want CONFIG_RT_GROUP_SCHED set.
-Mike
Quoted 36 lines · Mike Galbraith
Quoted 20 lines · torbenh
Quoted 19 lines · Mike Galbraith
Quoted 17 lines · torbenh
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.Quoted 6 lines
Quoted 2 lines
You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
but i can not get the same behaviour as if
CONFIG_RT_GROUP_SCHEDwas off. iE N cgroups with different cpu.share values, but each with rt_runtime_us=950000? if
CONFIG_RT_GROUP_SCHEDwas a noop, it wouldn't exist.Quoted 3 lines
if the
rt_runtime_uswas in a different subsystem, its my understanding that i could leavert_runtime_usalone, and have all tasks in the root group in thert_runtimesubsystem.Sounds like you just want to turn
CONFIG_RT_GROUP_SCHEDoff.
Quoted 7 lines
Quoted 5 lines
Quoted 2 lines
The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
sure it belongs to the user. but what if user wants to have different cpu.shares, but full
rt_runtime_usfor all tasks ?Then the user doesn't want
CONFIG_RT_GROUP_SCHEDset.
many users dont configure their kernels themselves. and this setting is not dynamic.
i guess its highly unlikely any normal user wants CONFIG_RT_GROUP_SCHED. but maybe distros will turn it on.
Signature · 1 line
torben Hohn
Quoted 28 lines · Mike Galbraith
Quoted 20 lines · torbenh
Quoted 19 lines · Mike Galbraith
Quoted 17 lines · torbenh
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.Quoted 6 lines
Quoted 2 lines
You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
but i can not get the same behaviour as if
CONFIG_RT_GROUP_SCHEDwas off. iE N cgroups with different cpu.share values, but each with rt_runtime_us=950000
Quoted 7 lines
? if
CONFIG_RT_GROUP_SCHEDwas a noop, it wouldn't exist.Quoted 3 lines
if the
rt_runtime_uswas in a different subsystem, its my understanding that i could leavert_runtime_usalone, and have all tasks in the root group in thert_runtimesubsystem.Sounds like you just want to turn
CONFIG_RT_GROUP_SCHEDoff.
but distros turn it on.
we could prevent debian from turning it on.
now opensuse 11.4 has turned it on.
Quoted 8 lines
Quoted 6 lines
Quoted 3 lines
The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
sure it belongs to the user. but what if user wants to have different cpu.shares, but full
rt_runtime_usfor all tasks ?Then the user doesn't want
CONFIG_RT_GROUP_SCHEDset.
but distros force it onto the user.
if systemd shows up, and puts things into different cgroups, we end up with a pretty fragmented rt_runtime_us.
Quoted 8 lines
-Mike
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to [email protected]
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Signature · 1 line
torben Hohn
Quoted 35 lines · torbenh
Quoted 34 lines · Mike Galbraith
Quoted 20 lines · torbenh
Quoted 19 lines · Mike Galbraith
Quoted 17 lines · torbenh
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.Quoted 6 lines
Quoted 2 lines
You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
but i can not get the same behaviour as if
CONFIG_RT_GROUP_SCHEDwas off. iE N cgroups with different cpu.share values, but each with rt_runtime_us=950000? if
CONFIG_RT_GROUP_SCHEDwas a noop, it wouldn't exist.Quoted 3 lines
if the
rt_runtime_uswas in a different subsystem, its my understanding that i could leavert_runtime_usalone, and have all tasks in the root group in thert_runtimesubsystem.
Quoted 5 lines
Quoted 1 line
Sounds like you just want to turn
CONFIG_RT_GROUP_SCHEDoff.but distros turn it on.
we could prevent debian from turning it on.
now opensuse 11.4 has turned it on.
If you or anyone else turns on RT_GROUP_SCHED, you will count your beans, and pay up front, or you will not play. That's a very sensible policy for realtime.
Quoted 11 lines
Quoted 7 lines
Quoted 5 lines
Quoted 2 lines
The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
sure it belongs to the user. but what if user wants to have different cpu.shares, but full
rt_runtime_usfor all tasks ?Then the user doesn't want
CONFIG_RT_GROUP_SCHEDset.but distros force it onto the user.
if systemd shows up, and puts things into different cgroups, we end up with a pretty fragmentedrt_runtime_us.
If systemd deals with it at all, seems to me it can only make a mess of it. But who knows, maybe they made a clever allocator. If they didn't, they'll need an escape hatch methinks.
-Mike
Quoted 38 lines · Mike Galbraith
Quoted 37 lines · torbenh
Quoted 35 lines · Mike Galbraith
Quoted 20 lines · torbenh
Quoted 19 lines · Mike Galbraith
Quoted 17 lines · torbenh
Quoted 11 lines · Peter Zijlstra
Quoted 8 lines · Mike Galbraith
sched, autogroup: fix
CONFIG_RT_GROUP_SCHEDsched_setscheduler()failure.If
CONFIG_RT_GROUP_SCHEDis set,__sched_setscheduler()fails due to autogroup not allocatingrt_runtime. Free unused/unusablert_seandrt_rq, redirect RT tasks to the root task group, and tell__sched_setscheduler()that it's ok.Signed-off-by Mike Galbraith <[email protected]>Reported-by Bharata B Rao <[email protected]>Thanks, applied!
while this behaviour is certeinly necessary, i think this is a hack. it fixes the problem for autogroups.
But its not fixed for things which want to control the cfs shares via normal cgroups.Quoted 6 lines
Quoted 2 lines
You mean automated control ala systemd? For a static set of groups, it works fine. I was wondering how systemd would deal with it.
but i can not get the same behaviour as if
CONFIG_RT_GROUP_SCHEDwas off. iE N cgroups with different cpu.share values, but each with rt_runtime_us=950000? if
CONFIG_RT_GROUP_SCHEDwas a noop, it wouldn't exist.Quoted 3 lines
if the
rt_runtime_uswas in a different subsystem, its my understanding that i could leavert_runtime_usalone, and have all tasks in the root group in thert_runtimesubsystem.Sounds like you just want to turn
CONFIG_RT_GROUP_SCHEDoff.
Quoted 7 lines
Quoted 3 lines
but distros turn it on.
we could prevent debian from turning it on.
now opensuse 11.4 has turned it on.If you or anyone else turns on
RT_GROUP_SCHED, you will count your beans, and pay up front, or you will not play. That's a very sensible policy for realtime.
this probably means that generic computer distros should not turn this option on ?
Quoted 9 lines
Quoted 9 lines
Quoted 8 lines
Quoted 6 lines
Quoted 3 lines
The allocation problem was shamelessly punted back to the user, where I think it truly belongs.
sure it belongs to the user. but what if user wants to have different cpu.shares, but full
rt_runtime_usfor all tasks ?Then the user doesn't want
CONFIG_RT_GROUP_SCHEDset.
Quoted 7 lines
Quoted 3 lines
but distros force it onto the user.
if systemd shows up, and puts things into different cgroups, we end up with a pretty fragmentedrt_runtime_us.If systemd deals with it at all, seems to me it can only make a mess of it. But who knows, maybe they made a clever allocator. If they didn't, they'll need an escape hatch methinks.
the problem is that audio applications can not really pre allocate their cpu needs. user can add processing plugins until he pushes his machine to the limit. (or the cgroup where his process is running in)
we dont really have a mechanism for plugins to publish their needed cycles.
Signature · 1 line
torben Hohn
Quoted 11 lines · torbenh
Quoted 9 lines · Mike Galbraith
Quoted 7 lines · torbenh
Quoted 1 line · Mike Galbraith
Sounds like you just want to turn
CONFIG_RT_GROUP_SCHEDoff.but distros turn it on.
we could prevent debian from turning it on.
now opensuse 11.4 has turned it on.
Quoted 6 lines
Quoted 3 lines
If you or anyone else turns on
RT_GROUP_SCHED, you will count your beans, and pay up front, or you will not play. That's a very sensible policy for realtime.this probably means that generic computer distros should not turn this option on ?
Yeah, agreed, not for a great default config, but only because newfangled automation thingies can't (possibly?) deal with it sanely.
Quoted 10 lines
Quoted 3 lines
If systemd deals with it at all, seems to me it can only make a mess of it. But who knows, maybe they made a clever allocator. If they didn't, they'll need an escape hatch methinks.
the problem is that audio applications can not really pre allocate their cpu needs. user can add processing plugins until he pushes his machine to the limit. (or the cgroup where his process is running in)
we dont really have a mechanism for plugins to publish their needed cycles.
I can't see how it could matter what any individual group of arbitrary groups N (who can appear/disappear in the blink of an eye) advertises as it's wish of the instant. "Hard" + "Arbitrary" doesn't compute for me.
-Mike
sorry... i cced the old ML addresses :S
fixing the CC now.
Quoted 16 lines · Mike Galbraith
Quoted 15 lines · torbenh
Quoted 12 lines · Mike Galbraith
Quoted 7 lines · torbenh
Quoted 1 line · Mike Galbraith
Sounds like you just want to turn
CONFIG_RT_GROUP_SCHEDoff.but distros turn it on.
we could prevent debian from turning it on.
now opensuse 11.4 has turned it on.If you or anyone else turns on
RT_GROUP_SCHED, you will count your beans, and pay up front, or you will not play. That's a very sensible policy for realtime.
Quoted 5 lines
Quoted 2 lines
this probably means that generic computer distros should not turn this option on ?
Yeah, agreed, not for a great default config, but only because newfangled automation thingies can't (possibly?) deal with it sanely.
but this is excactly the reason, why i would advocate rt_runtime to be in a separate cgroups system.
any admin who wants to limit RT runtime could still do it. people who dont care, and just want their cfs slices configured, can still do it.
Quoted 9 lines
Quoted 9 lines
Quoted 4 lines
If systemd deals with it at all, seems to me it can only make a mess of it. But who knows, maybe they made a clever allocator. If they didn't, they'll need an escape hatch methinks.
the problem is that audio applications can not really pre allocate their cpu needs. user can add processing plugins until he pushes his machine to the limit. (or the cgroup where his process is running in)
Quoted 6 lines
Quoted 2 lines
we dont really have a mechanism for plugins to publish their needed cycles.
I can't see how it could matter what any individual group of arbitrary groups N (who can appear/disappear in the blink of an eye) advertises as it's wish of the instant. "Hard" + "Arbitrary" doesn't compute for me.
i dont really understnad this statement.
Quoted 8 lines
-Mike
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to [email protected]
More majordomo info at http://vger.kernel.org/majordomo-info.html
Please read the FAQ at http://www.tux.org/lkml/
Signature · 1 line
torben Hohn
Quoted 1 line · torbenh
i dont really understnad this statement.
Doesn't matter, we're thinking about different subjects. You're thinking of an unborn mechanism, I'm thinking of the living one.
-Mike
P.S. Kindly do not CC closed lists. Closed list readers only see your part of any conversation, and anyone replying to you is rewarded with bounce spam for their trouble.
Quoted 3 lines · Mike Galbraith
P.S. Kindly do not CC closed lists. Closed list readers only see your part of any conversation, and anyone replying to you is rewarded with bounce spam for their trouble.
yeah. sorry. i thought the lists were open.
there doesnt seem to be interest in it anyways.
i guess i rest my case, and wait for things to fall apart.
Signature · 1 line
torben Hohn
[tip:sched/urgent] sched, autogroup: Fix CONFIG_RT_GROUP_SCHED sched_setscheduler() failure
In reply to Mike GalbraithCommit-ID: f44937718ce3b8360f72f6c68c9481712517a867 Gitweb: http://git.kernel.org/tip/f44937718ce3b8360f72f6c68c9481712517a867 Author: Mike Galbraith <[email protected]> AuthorDate: Thu, 13 Jan 2011 04:54:50 +0100 Committer: Ingo Molnar <[email protected]> CommitDate: Tue, 18 Jan 2011 15:09:42 +0100
sched, autogroup: Fix CONFIG_RT_GROUP_SCHED sched_setscheduler() failure
If CONFIG_RT_GROUP_SCHED is set, __sched_setscheduler() fails due to autogroup not allocating rt_runtime. Free unused/unusable rt_se and rt_rq, redirect RT tasks to the root task group, and tell __sched_setscheduler() that it's ok.
LKML-Reference: <[email protected]>
--- kernel/sched.c | 3 ++- kernel/sched_autogroup.c | 27 +++++++++++++++++++++++++++ kernel/sched_autogroup.h | 4 ++++ 3 files changed, 33 insertions(+), 1 deletions(-)
kernel/sched.c +2 -1
@@ -4871,7 +4871,8 @@ recheck:* assigned. */ if (rt_bandwidth_enabled () &&rt_policy (policy) && -task_group (p)->rt_bandwidth.rt_runtime ==0 ) { +task_group (p)->rt_bandwidth.rt_runtime ==0 && + !task_group_is_autogroup (task_group (p))) {__task_rq_unlock (rq);raw_spin_unlock_irqrestore (&p->pi_lock, flags);return -EPERM ;
kernel/sched_autogroup.c +27 -0
@@ -27,6 +27,11 @@ static inline void autogroup_destroy(struct kref *kref) { struct autogroup *ag = container_of(kref, struct autogroup, kref); +#ifdef CONFIG_RT_GROUP_SCHED +/* We've redirected RT tasks to the root task group... */ + ag->tg->rt_se =NULL ; + ag->tg->rt_rq =NULL ; +#endif sched_destroy_group (ag->tg); }
@@ -55,6 +60,10 @@ static inline struct autogroup *autogroup_task_get(struct task_struct *p)return ag; } +#ifdef CONFIG_RT_GROUP_SCHED +static void free_rt_sched_group (struct task_group *tg); +#endif +static inline struct autogroup *autogroup_create (void ) {struct autogroup *ag =kzalloc (sizeof (*ag),GFP_KERNEL );
@@ -72,6 +81,19 @@ static inline struct autogroup *autogroup_create(void)init_rwsem (&ag->lock); ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* Autogroup RT tasks are redirected to the root task group +* so we don't have to move tasks around upon policy change, +* or flail around trying to allocate bandwidth on the fly. +* A bandwidth exception in __sched_setscheduler() allows +* the policy change to proceed. Thereafter, task_group() +* returns &root_task_group, so zero bandwidth is required. +*/ +free_rt_sched_group (tg); + tg->rt_se = root_task_group.rt_se; + tg->rt_rq = root_task_group.rt_rq; +#endif tg->autogroup = ag;return ag;
@@ -106,6 +128,11 @@ task_wants_autogroup(struct task_struct *p, struct task_group *tg)return true; } +static inline bool task_group_is_autogroup (struct task_group *tg) +{ +return tg != &root_task_group && tg->autogroup; +} +static inline struct task_group *autogroup_task_group (struct task_struct *p,struct task_group *tg) {
kernel/sched_autogroup.h +4 -0
@@ -15,6 +15,10 @@ autogroup_task_group(struct task_struct *p, struct task_group *tg);static inline void autogroup_init (struct task_struct *init_task) { }static inline void autogroup_free (struct task_group *tg) { } +static inline bool task_group_is_autogroup (struct task_group *tg) +{ +return 0 ; +}static inline struct task_group *autogroup_task_group (struct task_struct *p,struct task_group *tg)
Quoted 21 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id = atomic_inc_return(&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED + /* + * HACK: autogroup RT tasks run in the root task group. + * This fools __sched_setscheduler() into proceeding on + * so we can move the task to the appropriate runqueue + * upon scheduling policy change. + */ + tg->rt_bandwidth.rt_runtime = RUNTIME_INF; +#endif return ag;
kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 159
Quoted 8 lines
kernel/sched_autogroup.c +5
-0@@ -143,6 +152,15 @@ autogroup_move_group(struct task_struct autogroup_kref_put(prev); } +static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ + if (p->sched_class->task_move_group) + p->sched_class->task_move_group(p, on_rq);
This will be called even if we don't change the sched_class in which case it is not necessary.
Thanks,
Yong
Signature · 1 line
Only stand for myself
Quoted 25 lines · Yong Zhang
Quoted 24 lines · Mike Galbraith
Index:
linux-2.6/kernel/sched_autogroup.c
===================================================================kernel/sched_autogroup.c +9
-0@@ -73,6 +73,15 @@ static inline struct autogroup *autogrou ag->id =atomic_inc_return (&autogroup_seq_nr); ag->tg = tg; tg->autogroup = ag; +#ifdef CONFIG_RT_GROUP_SCHED +/* +* HACK: autogroup RT tasks run in the root task group. +* This fools __sched_setscheduler() into proceeding on +* so we can move the task to the appropriate runqueue +* upon scheduling policy change. +*/ + tg->rt_bandwidth.rt_runtime =RUNTIME_INF ; +#endif return ag;@@ -143,6 +152,15 @@ autogroup_move_group(struct task_structautogroup_kref_put (prev); }
Quoted 8 lines
kernel/sched_autogroup.c autogroup_move_group(struct task_struct · line 159
Quoted 5 lines
kernel/sched_autogroup.c +5
-0+static inline void +autogroup_setscheduler (struct task_struct *p,int on_rq) +{ +if (p->sched_class->task_move_group) + p->sched_class->task_move_group (p, on_rq);This will be called even if we don't change the
sched_classin which case it is not necessary.
Yes. It'll also piddle around with tasks it shouldn't. I sent what I hope is a better solution a few minutes ago. This one works, but probably upset Peter's tummy mightily :)
-Mike