File 19770-x86-amd-s3-resume.patch of Package xen

# HG changeset patch
# User Keir Fraser <keir.fraser@citrix.com>
# Date 1245158374 -3600
# Node ID 64a932c92a7c0c6e5e027b55718f5fff2aac9e9c
# Parent  2d68d518038b70bdb1cdb3eb078f1d394dd08437
x86: fix s3 resume on AMD CPUs

Avoid longjmp as it has different semantics than on Intel CPUs in long
mode. Also add a few comments and remove a pointless reload of DS.

Signed-off-by: Christoph Egger <Christoph.Egger@amd.com>
Signed-off-by: Keir Fraser <keir.fraser@eu.citrix.com>

--- a/xen/arch/x86/acpi/wakeup_prot.S
+++ b/xen/arch/x86/acpi/wakeup_prot.S
@@ -142,6 +142,12 @@ __ret_point:
         LOAD_GREG(sp)
 
 #if defined(__x86_64__)
+        /* Reload code selector */
+        pushq   $(__HYPERVISOR_CS64)
+        leaq    1f(%rip),%rax
+        pushq   %rax
+        lretq
+1:
 
         mov     REF(saved_cr8), %rax
         mov     %rax, %cr8
--- a/xen/arch/x86/boot/wakeup.S
+++ b/xen/arch/x86/boot/wakeup.S
@@ -110,6 +110,7 @@ video_flags:    .long 0
         # Add offset for any reference to xen specific symbols
 
 wakeup_32:
+        /* Set up segment registers and initial stack for protected mode */
         mov     $BOOT_DS, %eax
         mov     %eax, %ds
         mov     %eax, %ss
@@ -152,6 +153,7 @@ wakeup_32:
 
         wbinvd
 
+        /* Enable paging and flush prefetch queue */
         mov     $0x80050033,%eax /* hi-to-lo: PG,AM,WP,NE,ET,MP,PE */
         mov     %eax,%cr0
         jmp     1f
@@ -163,31 +165,22 @@ wakeup_32:
         ljmp    $BOOT_CS64, $bootsym_phys(wakeup_64)
 
         .code64
-        .align  8
-        .word   0,0,0
-lgdt_descr:
-        .word   LAST_RESERVED_GDT_BYTE
-        .quad   boot_cpu_gdt_table - FIRST_RESERVED_GDT_BYTE
-        
 wakeup_64:
-        lgdt    lgdt_descr(%rip)
-        mov     $(__HYPERVISOR_DS64), %eax
-        mov     %eax, %ds
-
-        # long jump to return point, with cs reload
-        rex64 ljmp    *ret_point(%rip)
+        /* Jump to high mappings and the higher-level wakeup code. */
+        movq    ret_point(%rip), %rbx
+        jmp     *%rbx
 
-        .align 8
 ret_point:
         .quad   __ret_point
-        .word   __HYPERVISOR_CS64
 
 #else /* !defined(__x86_64__) */
+
         lgdt    gdt_descr
         mov     $(__HYPERVISOR_DS), %eax
         mov     %eax, %ds
 
         ljmp    $(__HYPERVISOR_CS), $__ret_point
+
 #endif
 
 bogus_saved_magic:
openSUSE Build Service is sponsored by