[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index] [Xen-changelog] [xen-unstable] PV-on-HVM: More carefully synchronise with APs when putting them to
# HG changeset patch # User kfraser@xxxxxxxxxxxxxxxxxxxxx # Date 1176376198 -3600 # Node ID 4c06bcd83c902cf9851e8ad7ada5c09207da3e91 # Parent 9e9eb5b3dab7d2a09c0ba157c0fea628bbcac957 PV-on-HVM: More carefully synchronise with APs when putting them to sleep in a spin loop. Signed-off-by: Keir Fraser <keir@xxxxxxxxxxxxx> --- unmodified_drivers/linux-2.6/platform-pci/machine_reboot.c | 34 ++++++++++--- 1 files changed, 27 insertions(+), 7 deletions(-) diff -r 9e9eb5b3dab7 -r 4c06bcd83c90 unmodified_drivers/linux-2.6/platform-pci/machine_reboot.c --- a/unmodified_drivers/linux-2.6/platform-pci/machine_reboot.c Thu Apr 12 11:44:26 2007 +0100 +++ b/unmodified_drivers/linux-2.6/platform-pci/machine_reboot.c Thu Apr 12 12:09:58 2007 +0100 @@ -6,21 +6,32 @@ #include "platform-pci.h" #include <asm/hypervisor.h> +struct ap_suspend_info { + int do_spin; + atomic_t nr_spinning; +}; + /* * Spinning prevents, for example, APs touching grant table entries while * the shared grant table is not mapped into the address space imemdiately * after resume. */ -static void ap_suspend(void *_ap_spin) +static void ap_suspend(void *_info) { - int *ap_spin = _ap_spin; + struct ap_suspend_info *info = _info; BUG_ON(!irqs_disabled()); - while (*ap_spin) { + atomic_inc(&info->nr_spinning); + mb(); + + while (info->do_spin) { cpu_relax(); HYPERVISOR_yield(); } + + mb(); + atomic_dec(&info->nr_spinning); } static int bp_suspend(void) @@ -42,7 +53,8 @@ static int bp_suspend(void) int __xen_suspend(int fast_suspend) { - int err, suspend_cancelled, ap_spin; + int err, suspend_cancelled, nr_cpus; + struct ap_suspend_info info; xenbus_suspend(); @@ -51,22 +63,30 @@ int __xen_suspend(int fast_suspend) /* Prevent any races with evtchn_interrupt() handler. */ disable_irq(xen_platform_pdev->irq); - ap_spin = 1; + info.do_spin = 1; + atomic_set(&info.nr_spinning, 0); smp_mb(); - err = smp_call_function(ap_suspend, &ap_spin, 0, 0); + nr_cpus = num_online_cpus() - 1; + + err = smp_call_function(ap_suspend, &info, 0, 0); if (err < 0) { preempt_enable(); xenbus_suspend_cancel(); return err; } + while (atomic_read(&info.nr_spinning) != nr_cpus) + cpu_relax(); + local_irq_disable(); suspend_cancelled = bp_suspend(); local_irq_enable(); smp_mb(); - ap_spin = 0; + info.do_spin = 0; + while (atomic_read(&info.nr_spinning) != 0) + cpu_relax(); enable_irq(xen_platform_pdev->irq); _______________________________________________ Xen-changelog mailing list Xen-changelog@xxxxxxxxxxxxxxxxxxx http://lists.xensource.com/xen-changelog
|
Lists.xenproject.org is hosted with RackSpace, monitoring our |