Skip to contentSkip to conversation

x86_64: system call and exception handling for compatibility mode guest (version 2)

RFC PATCH New Jan Beulich 1 participant 1 message Aug 25, 2006

lore
Share & tools
lore
#0 lore raw

RFC PATCH 2/4 x86_64: system call and exception handling for compatibility mode guest (version 2)

This adds several routines and conditionals to deal with the specifics of compatibility mode guests. Compatibility mode hypercall handlers are being stubbed out to crash the domain for the time being.

xen/arch/x86/traps.c +6 -0
Index: 2006-08-16/xen/arch/x86/traps.c
===================================================================
@@ -137,6 +137,12 @@ static void show_guest_stack(struct cpu_
     if ( hvm_guest(current) )
         return;
 
+    if ( IS_COMPAT(container_of(regs, struct cpu_info, guest_cpu_user_regs)->current_vcpu->domain) )
+    {
+        compat_show_guest_stack(regs, debug_stack_lines);
+        return;
+    }
+
     if ( vm86_mode(regs) )
     {
         stack = (unsigned long *)((regs->ss << 4) + (regs->esp & 0xffff));
xen/arch/x86/x86_64/Makefile +6 -0
Index: 2006-08-16/xen/arch/x86/x86_64/Makefile
===================================================================
@@ -1,3 +1,9 @@
 obj-y += entry.o
 obj-y += mm.o
 obj-y += traps.o
+
+ifeq ($(CONFIG_COMPAT),y)
+# extra dependencies
+entry.o: compat/entry.S
+traps.o: compat/traps.c
+endif
xen/arch/x86/x86_64/asm-offsets.c +5 -0
Index: 2006-08-16/xen/arch/x86/x86_64/asm-offsets.c
===================================================================
@@ -53,6 +53,7 @@ void __dummy__(void)
     BLANK();
 
     OFFSET(VCPU_processor, struct vcpu, processor);
+    OFFSET(VCPU_domain, struct vcpu, domain);
     OFFSET(VCPU_vcpu_info, struct vcpu, vcpu_info);
     OFFSET(VCPU_trap_bounce, struct vcpu, arch.trap_bounce);
     OFFSET(VCPU_thread_flags, struct vcpu, arch.flags);
@@ -86,6 +87,10 @@ void __dummy__(void)
     OFFSET(VCPU_vmx_launched, struct vcpu, arch.hvm_vmx.launched);
     BLANK();
 
+    OFFSET(DOMAIN_domain_flags, struct domain, domain_flags);
+    DEFINE(_DOMF_compat, _DOMF_compat);
+    BLANK();
+
     OFFSET(VMCB_rax, struct vmcb_struct, rax);
     OFFSET(VMCB_tsc_offset, struct vmcb_struct, tsc_offset);
     BLANK();
xen/arch/x86/x86_64/compat/entry.S new file +369 -0

369 lines not on this page · raw message

xen/arch/x86/x86_64/compat/traps.c new file +264 -0

264 lines not on this page · raw message

xen/arch/x86/x86_64/entry.S +18 -2
Index: 2006-08-16/xen/arch/x86/x86_64/entry.S
===================================================================
@@ -334,8 +334,15 @@ domain_crash_synchronous:
 ENTRY(ret_from_intr)
         GET_CURRENT(%rbx)
         testb $3,UREGS_cs(%rsp)
-        jnz   test_all_events
-        jmp   restore_all_xen
+        jz    restore_all_xen
+#ifndef CONFIG_COMPAT
+        jmp   test_all_events
+#else
+        movq  VCPU_domain(%rbx),%rax
+        btl   $_DOMF_compat, DOMAIN_domain_flags(%rax)
+        jnc   test_all_events
+        jmp   compat_test_all_events
+#endif
 
         ALIGN
 /* No special register assumptions. */
@@ -353,6 +360,11 @@ handle_exception:
         testb $3,UREGS_cs(%rsp)
         jz    restore_all_xen
         leaq  VCPU_trap_bounce(%rbx),%rdx
+#ifdef CONFIG_COMPAT
+        movq  VCPU_domain(%rbx),%rax
+        btl   $_DOMF_compat, DOMAIN_domain_flags(%rax)
+        jc    compat_post_handle_exception
+#endif
         testb $TBF_EXCEPTION,TRAPBOUNCE_flags(%rdx)
         jz    test_all_events
         call  create_bounce_frame
@@ -612,3 +624,7 @@ ENTRY(hypercall_args_table)
         .rept NR_hypercalls-(.-hypercall_args_table)
         .byte 0 /* do_ni_hypercall      */
         .endr
+
+#ifdef CONFIG_COMPAT
+#include "compat/entry.S"
+#endif
xen/arch/x86/x86_64/traps.c +11 -1
Index: 2006-08-16/xen/arch/x86/x86_64/traps.c
===================================================================
@@ -228,6 +228,7 @@ unsigned long do_iret(void)
 }
 
 asmlinkage void syscall_enter(void);
+asmlinkage void compat_hypercall(void);
 void __init percpu_traps_init(void)
 {
     char *stack_bottom, *stack;
@@ -239,6 +240,11 @@ void __init percpu_traps_init(void)
         set_intr_gate(TRAP_double_fault, &double_fault);
         idt_table[TRAP_double_fault].a |= 1UL << 32; /* IST1 */
         idt_table[TRAP_nmi].a          |= 2UL << 32; /* IST2 */
+
+#ifdef CONFIG_COMPAT
+        /* The hypercall entry vector is only accessible from ring 1. */
+        _set_gate(idt_table+HYPERCALL_VECTOR, 15, 1, &compat_hypercall);
+#endif
     }
 
     stack_bottom = (char *)get_stack_bottom();
@@ -479,12 +485,16 @@ static void hypercall_page_initialise_ri
     *(u16 *)(p+ 9) = 0x050f;  /* syscall */
 }
 
+#include "compat/traps.c"
+
 void hypercall_page_initialise(struct domain *d, void *hypercall_page)
 {
     if ( hvm_guest(d->vcpu[0]) )
         hvm_hypercall_page_initialise(d, hypercall_page);
-    else
+    else if ( !IS_COMPAT(d) )
         hypercall_page_initialise_ring3_kernel(hypercall_page);
+    else
+        hypercall_page_initialise_ring1_kernel(hypercall_page);
 }
 
 /*
xen/include/asm-x86/processor.h +6 -0
Index: 2006-08-16/xen/include/asm-x86/processor.h
===================================================================
@@ -558,6 +558,12 @@ void show_execution_state(struct cpu_use
 void show_page_walk(unsigned long addr);
 asmlinkage void fatal_trap(int trapnr, struct cpu_user_regs *regs);
 
+#ifdef CONFIG_COMPAT
+void compat_show_guest_stack(struct cpu_user_regs *, int lines);
+#else
+#define compat_show_guest_stack(regs, lines) ((void)0)
+#endif
+
 /* Dumps current register and stack state. */
 #define dump_execution_state()                                              \
     /* NB. Needs interrupts enabled else we end up in fatal_trap(). */      \

_______________________________________________
Xen-devel mailing list
[email protected]
http://lists.xensource.com/xen-devel