From 311342d796822aead26a29d0ad69696818387a26 Mon Sep 17 00:00:00 2001 From: Pavankumar Kondeti Date: Thu, 28 Feb 2019 10:40:39 +0530 Subject: [PATCH] cpuset: Restore tasks affinity while moving across cpusets When tasks move across cpusets, the current affinity settings are lost. Cache the task affinity and restore it during cpuset migration. The restoring happens only when the cached affinity is subset of the current cpuset settings. Change-Id: I6c2ec1d5e3d994e176926d94b9e0cc92418020cc Signed-off-by: Pavankumar Kondeti [satyap@codeaurora.org: fix trivial merge conflicts and replace cs->cpus_requested with cs->cpus_allowed] Signed-off-by: Satya Durga Srinivasu Prabhala --- include/linux/sched.h | 3 +++ init/init_task.c | 3 +++ kernel/cgroup/cpuset.c | 20 ++++++++++++++++++-- kernel/sched/core.c | 8 ++++++++ 4 files changed, 32 insertions(+), 2 deletions(-) diff --git a/include/linux/sched.h b/include/linux/sched.h index 0e92ee6464e5..eb32de4fdda7 100644 --- a/include/linux/sched.h +++ b/include/linux/sched.h @@ -860,6 +860,9 @@ struct task_struct { int nr_cpus_allowed; const cpumask_t *cpus_ptr; cpumask_t cpus_mask; +#ifdef CONFIG_SCHED_WALT + cpumask_t cpus_requested; +#endif #ifdef CONFIG_PREEMPT_RCU int rcu_read_lock_nesting; diff --git a/init/init_task.c b/init/init_task.c index af4dc7dcf246..2ad8a7c21c77 100644 --- a/init/init_task.c +++ b/init/init_task.c @@ -73,6 +73,9 @@ struct task_struct init_task .cpus_ptr = &init_task.cpus_mask, .cpus_mask = CPU_MASK_ALL, .nr_cpus_allowed= NR_CPUS, +#ifdef CONFIG_SCHED_WALT + .cpus_requested = CPU_MASK_ALL, +#endif .mm = NULL, .active_mm = &init_mm, .restart_block = { diff --git a/kernel/cgroup/cpuset.c b/kernel/cgroup/cpuset.c index c87ee6412b36..9ea6269fff29 100644 --- a/kernel/cgroup/cpuset.c +++ b/kernel/cgroup/cpuset.c @@ -1022,6 +1022,22 @@ void rebuild_sched_domains(void) put_online_cpus(); } +static int update_cpus_allowed(struct cpuset *cs, struct task_struct *p, + const struct cpumask *new_mask) +{ +#ifdef CONFIG_SCHED_WALT + int ret; + + if (cpumask_subset(&p->cpus_requested, cs->cpus_allowed)) { + ret = set_cpus_allowed_ptr(p, &p->cpus_requested); + if (!ret) + return ret; + } +#endif + + return set_cpus_allowed_ptr(p, new_mask); +} + /** * update_tasks_cpumask - Update the cpumasks of tasks in the cpuset. * @cs: the cpuset in which each task's cpus_allowed mask needs to be changed @@ -1037,7 +1053,7 @@ static void update_tasks_cpumask(struct cpuset *cs) css_task_iter_start(&cs->css, 0, &it); while ((task = css_task_iter_next(&it))) - set_cpus_allowed_ptr(task, cs->effective_cpus); + update_cpus_allowed(cs, task, cs->effective_cpus); css_task_iter_end(&it); } @@ -2187,7 +2203,7 @@ static void cpuset_attach(struct cgroup_taskset *tset) * can_attach beforehand should guarantee that this doesn't * fail. TODO: have a better way to handle failure here */ - WARN_ON_ONCE(set_cpus_allowed_ptr(task, cpus_attach)); + WARN_ON_ONCE(update_cpus_allowed(cs, task, cpus_attach)); cpuset_change_task_nodemask(task, &cpuset_attach_nodemask_to); cpuset_update_task_spread_flag(cs, task); diff --git a/kernel/sched/core.c b/kernel/sched/core.c index ba94863d96aa..b10f9c2300ae 100644 --- a/kernel/sched/core.c +++ b/kernel/sched/core.c @@ -5634,6 +5634,11 @@ again: retval = -EINVAL; } +#ifdef CONFIG_SCHED_WALT + if (!retval && !(p->flags & PF_KTHREAD)) + cpumask_and(&p->cpus_requested, in_mask, cpu_possible_mask); +#endif + out_free_new_mask: free_cpumask_var(new_mask); out_free_cpus_allowed: @@ -6780,6 +6785,9 @@ void __init sched_init_smp(void) /* Move init over to a non-isolated CPU */ if (set_cpus_allowed_ptr(current, housekeeping_cpumask(HK_FLAG_DOMAIN)) < 0) BUG(); +#ifdef CONFIG_SCHED_WALT + cpumask_copy(¤t->cpus_requested, cpu_possible_mask); +#endif sched_init_granularity(); init_sched_rt_class();