On 06/04/2014 02:49 PM, Peter Zijlstra wrote: > On Wed, Jun 04, 2014 at 10:27:25AM +0800, Lai Jiangshan wrote: >>> Hmm, yes I think you're right. A queued wakeup can miss an affinity >>> change like that. >>> >>> Something like the below ought to cure that I suppose.. >> >> As a non-scheduler developer, I can't find anything wrong with the patch >> (I searched all on_rq in kernel/sched). > > You did fine finding that hole, so who knows, you might become one real > soon now ;-) > >> but I think __migrate_task() is slow path comparing to sched_ttwu_pending(). >> So I prefer to change set_cpus_allowed_ptr() and __migrate_task() rather than >> to sched_ttwu_pending(). > > Yes, I agree, something there would be better, but I couldn't find > anything without holes in. > >
I think the following code works. (inspirited from the sched_ttwu_pending() in migration_call().) if p->on_rq == 0 && p->state == TASK_WAKING in __migrate_task() after this patch, it means the cpuallowed is changed before __migrate_task() along with other scheduler movements happens between sched_ttwu_pending() and __migrate_task(). diff --git a/kernel/sched/core.c b/kernel/sched/core.c index 268a45e..277f3bc 100644 --- a/kernel/sched/core.c +++ b/kernel/sched/core.c @@ -4530,7 +4530,7 @@ int set_cpus_allowed_ptr(struct task_struct *p, const struct cpumask *new_mask) goto out; dest_cpu = cpumask_any_and(cpu_active_mask, new_mask); - if (p->on_rq) { + if (p->on_rq || p->state == TASK_WAKING) { struct migration_arg arg = { p, dest_cpu }; /* Need help from migration thread: drop lock and wait. */ task_rq_unlock(rq, p, &flags); @@ -4656,6 +4656,7 @@ static int migration_cpu_stop(void *data) * be on another cpu but it doesn't matter. */ local_irq_disable(); + sched_ttwu_pending(); __migrate_task(arg->task, raw_smp_processor_id(), arg->dest_cpu); local_irq_enable(); return 0; -- To unsubscribe from this list: send the line "unsubscribe linux-kernel" in the body of a message to majord...@vger.kernel.org More majordomo info at http://vger.kernel.org/majordomo-info.html Please read the FAQ at http://www.tux.org/lkml/