[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[Xen-changelog] Fix x86/32 do_iret implementation, fixes VM86 mode.



# HG changeset patch
# User Ian.Campbell@xxxxxxxxxxxxx
# Node ID 19f5ffa02154db55a4fa5a67201e763d8626868b
# Parent  ec4ef8c5f04d9fef83acf5281a432a7821906520
Fix x86/32 do_iret implementation, fixes VM86 mode.

Do not clobber a freshly restored esp when performing an iret.

Signed-off-by: Keir Fraser <keir@xxxxxxxxxxxxx>
Signed-off-by: Ian Campbell <Ian.Campbell@xxxxxxxxxxxxx>

diff -r ec4ef8c5f04d -r 19f5ffa02154 xen/arch/x86/x86_32/traps.c
--- a/xen/arch/x86/x86_32/traps.c       Fri Jan 13 10:38:33 2006
+++ b/xen/arch/x86/x86_32/traps.c       Fri Jan 13 11:04:04 2006
@@ -157,14 +157,6 @@
         __asm__ __volatile__ ( "hlt" );
 }
 
-static inline void pop_from_guest_stack(
-    void *dst, struct cpu_user_regs *regs, unsigned int bytes)
-{
-    if ( unlikely(__copy_from_user(dst, (void __user *)regs->esp, bytes)) )
-        domain_crash_synchronous();
-    regs->esp += bytes;
-}
-
 asmlinkage unsigned long do_iret(void)
 {
     struct cpu_user_regs *regs = guest_cpu_user_regs();
@@ -175,22 +167,29 @@
         domain_crash_synchronous();
 
     /* Pop and restore EAX (clobbered by hypercall). */
-    pop_from_guest_stack(&regs->eax, regs, 4);
+    if ( unlikely(__copy_from_user(&regs->eax, (void __user *)regs->esp, 4)) )
+        domain_crash_synchronous();
+    regs->esp += 4;
 
     /* Pop and restore CS and EIP. */
-    pop_from_guest_stack(&regs->eip, regs, 8);
+    if ( unlikely(__copy_from_user(&regs->eip, (void __user *)regs->esp, 8)) )
+        domain_crash_synchronous();
+    regs->esp += 8;
 
     /*
      * Pop, fix up and restore EFLAGS. We fix up in a local staging area
      * to avoid firing the BUG_ON(IOPL) check in arch_getdomaininfo_ctxt.
      */
-    pop_from_guest_stack(&eflags, regs, 4);
+    if ( unlikely(__copy_from_user(&eflags, (void __user *)regs->esp, 4)) )
+        domain_crash_synchronous();
+    regs->esp += 4;
     regs->eflags = (eflags & ~X86_EFLAGS_IOPL) | X86_EFLAGS_IF;
 
     if ( VM86_MODE(regs) )
     {
         /* Return to VM86 mode: pop and restore ESP,SS,ES,DS,FS and GS. */
-        pop_from_guest_stack(&regs->esp, regs, 24);
+        if ( __copy_from_user(&regs->esp, (void __user *)regs->esp, 24) )
+            domain_crash_synchronous();
     }
     else if ( unlikely(RING_0(regs)) )
     {
@@ -199,7 +198,8 @@
     else if ( !RING_1(regs) )
     {
         /* Return to ring 2/3: pop and restore ESP and SS. */
-        pop_from_guest_stack(&regs->esp, regs, 8);
+        if ( __copy_from_user(&regs->esp, (void __user *)regs->esp, 8) )
+            domain_crash_synchronous();
     }
 
     /* No longer in NMI context. */

_______________________________________________
Xen-changelog mailing list
Xen-changelog@xxxxxxxxxxxxxxxxxxx
http://lists.xensource.com/xen-changelog


 


Rackspace

Lists.xenproject.org is hosted with RackSpace, monitoring our
servers 24x7x365 and backed by RackSpace's Fanatical Support®.