# HG changeset patch # User Ben Guthro # Date 1348555094 -7200 # Node ID c8d65d91a6f20fa7fae905bbf172e59b335d6371 # Parent b49f7bf52fa92626517386cba89350243b808871 x86/S3: add cache flush on secondary CPUs before going to sleep Secondary CPUs, between doing their final memory writes (particularly updating cpu_initialized) and getting a subsequent INIT, may not write back all modified data. The INIT itself then causes those modifications to be lost, so in the cpu_initialized case the CPU would find itself already initialized, (intentionally) entering an infinite loop instead of actually coming online. Signed-off-by: Ben Guthro Make acpi_dead_idle() call default_dead_idle() rather than duplicating the logic there. Signed-off-by: Jan Beulich Acked-by: Keir Fraser Committed-by: Jan Beulich --- a/xen/arch/x86/acpi/cpu_idle.c +++ b/xen/arch/x86/acpi/cpu_idle.c @@ -647,6 +647,12 @@ static void acpi_dead_idle(void) } default_halt: + /* + * When going into S3, without flushing caches modified data may be + * held by the CPUs spinning here indefinitely, and get discarded by + * a subsequent INIT. + */ + wbinvd(); for ( ; ; ) halt(); } --- a/xen/arch/x86/domain.c +++ b/xen/arch/x86/domain.c @@ -86,6 +86,12 @@ static void default_idle(void) static void default_dead_idle(void) { + /* + * When going into S3, without flushing caches modified data may be + * held by the CPUs spinning here indefinitely, and get discarded by + * a subsequent INIT. + */ + wbinvd(); for ( ; ; ) halt(); }