diff options
author | Juergen Gross <juergen.gross@ts.fujitsu.com> | 2011-03-15 10:14:27 +0000 |
---|---|---|
committer | Juergen Gross <juergen.gross@ts.fujitsu.com> | 2011-03-15 10:14:27 +0000 |
commit | e1255ac77ed688d843b207ebdf2d0e6ca3fc6583 (patch) | |
tree | cb989606ee8405334cf8f22a50a18c6e9e7c2ec8 /xen/common/schedule.c | |
parent | 436308d761e9f1a580f35cc69abb4d594b6fe4fb (diff) | |
download | xen-e1255ac77ed688d843b207ebdf2d0e6ca3fc6583.tar.gz xen-e1255ac77ed688d843b207ebdf2d0e6ca3fc6583.tar.bz2 xen-e1255ac77ed688d843b207ebdf2d0e6ca3fc6583.zip |
Avoid endless loop for vcpu migration.
Only call SCHED_OP(pick_cpu) if a previously picked cpu is not
suitable on the current iteration of the retry loop.
Signed-off-by: Juergen Gross <juergen.gross@ts.fujitsu.com>
Signed-off-by: Keir Fraser <keir@xen.org>
Diffstat (limited to 'xen/common/schedule.c')
-rw-r--r-- | xen/common/schedule.c | 22 |
1 files changed, 21 insertions, 1 deletions
diff --git a/xen/common/schedule.c b/xen/common/schedule.c index e89da7a34b..129abe44e4 100644 --- a/xen/common/schedule.c +++ b/xen/common/schedule.c @@ -395,6 +395,7 @@ static void vcpu_migrate(struct vcpu *v) unsigned long flags; unsigned int old_cpu, new_cpu; spinlock_t *old_lock, *new_lock; + bool_t pick_called = 0; old_cpu = new_cpu = v->processor; for ( ; ; ) @@ -426,14 +427,33 @@ static void vcpu_migrate(struct vcpu *v) spin_lock(old_lock); } - /* Select new CPU. */ old_cpu = v->processor; if ( old_lock == per_cpu(schedule_data, old_cpu).schedule_lock ) { + /* + * If we selected a CPU on the previosu iteration, check if it + * remains suitable for running this vCPU. + */ + if ( pick_called && + (new_lock == per_cpu(schedule_data, new_cpu).schedule_lock) && + cpu_isset(new_cpu, v->cpu_affinity) && + cpu_isset(new_cpu, v->domain->cpupool->cpu_valid) ) + break; + + /* Select a new CPU. */ new_cpu = SCHED_OP(VCPU2OP(v), pick_cpu, v); if ( (new_lock == per_cpu(schedule_data, new_cpu).schedule_lock) && cpu_isset(new_cpu, v->domain->cpupool->cpu_valid) ) break; + pick_called = 1; + } + else + { + /* + * We do not hold the scheduler lock appropriate for this vCPU. + * Thus we cannot select a new CPU on this iteration. Try again. + */ + pick_called = 0; } if ( old_lock != new_lock ) |