source: trunk/packages/xen-3.1/xen-3.1/tools/firmware/vmxassist/trap.S @ 34

Last change on this file since 34 was 34, checked in by hartmans, 18 years ago

Add xen and xen-common

File size: 4.9 KB
Line 
1/*
2 * trap.S: Trap and world switch handlers
3 *
4 * Leendert van Doorn, leendert@watson.ibm.com
5 * Copyright (c) 2005, International Business Machines Corporation.
6 *
7 * This program is free software; you can redistribute it and/or modify it
8 * under the terms and conditions of the GNU General Public License,
9 * version 2, as published by the Free Software Foundation.
10 *
11 * This program is distributed in the hope it will be useful, but WITHOUT
12 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
13 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
14 * more details.
15 *
16 * You should have received a copy of the GNU General Public License along with
17 * this program; if not, write to the Free Software Foundation, Inc., 59 Temple
18 * Place - Suite 330, Boston, MA 02111-1307 USA.
19 */
20#include "machine.h"
21#include "vm86.h"
22#include "offsets.h"
23
24/*
25 * All processor exception/faults/interrupts end up here.
26 *
27 * On an exception/fault, the processor pushes CS:EIP, SS, ESP and an
28 * optional error code onto the stack. The common_trap routine
29 * below saves the processor context and transfers control to trap()
30 * whose job it is to virtualize and pass on the trap.
31 */
32        .macro  TRAP_HANDLER trapno error
33        .text
34        .align  16
351:      .if     \error == 0
36        pushl   $0                      /* dummy error code */
37        .endif
38        pushl   $\trapno
39        jmp     common_trap
40        .section .rodata
41        .long   1b
42        .text
43        .endm
44
45        .section .rodata
46        .code32
47        .align  4
48        .global trap_handlers
49trap_handlers:
50        TRAP_HANDLER    0, 0    /* divide error */
51        TRAP_HANDLER    1, 0    /* debug */
52        TRAP_HANDLER    2, 0    /* NMI interrupt */
53        TRAP_HANDLER    3, 0    /* breakpoint */
54        TRAP_HANDLER    4, 0    /* overflow */
55        TRAP_HANDLER    5, 0    /* BOUND range exceeded */
56        TRAP_HANDLER    6, 0    /* invalid opcode */
57        TRAP_HANDLER    7, 0    /* device not available */
58        TRAP_HANDLER    8, 1    /* double fault */
59        TRAP_HANDLER    9, 0    /* coprocessor segment overrun */
60        TRAP_HANDLER    10, 1   /* invalid TSS */
61        TRAP_HANDLER    11, 1   /* segment not present */
62        TRAP_HANDLER    12, 1   /* stack-segment fault */
63        TRAP_HANDLER    13, 1   /* general protection */
64        TRAP_HANDLER    14, 1   /* page fault */
65        TRAP_HANDLER    15, 0   /* reserved */
66        TRAP_HANDLER    16, 0   /* FPU floating-point error */
67        TRAP_HANDLER    17, 1   /* alignment check */
68        TRAP_HANDLER    18, 0   /* machine check */
69        TRAP_HANDLER    19, 0   /* SIMD floating-point error */
70        TRAP_HANDLER    20, 0   /* reserved */
71        TRAP_HANDLER    21, 0   /* reserved */
72        TRAP_HANDLER    22, 0   /* reserved */
73        TRAP_HANDLER    23, 0   /* reserved */
74        TRAP_HANDLER    24, 0   /* reserved */
75        TRAP_HANDLER    25, 0   /* reserved */
76        TRAP_HANDLER    26, 0   /* reserved */
77        TRAP_HANDLER    27, 0   /* reserved */
78        TRAP_HANDLER    28, 0   /* reserved */
79        TRAP_HANDLER    29, 0   /* reserved */
80        TRAP_HANDLER    30, 0   /* reserved */
81        TRAP_HANDLER    31, 0   /* reserved */
82        TRAP_HANDLER    32, 0   /* irq 0 */
83        TRAP_HANDLER    33, 0   /* irq 1 */
84        TRAP_HANDLER    34, 0   /* irq 2 */
85        TRAP_HANDLER    35, 0   /* irq 3 */
86        TRAP_HANDLER    36, 0   /* irq 4 */
87        TRAP_HANDLER    37, 0   /* irq 5 */
88        TRAP_HANDLER    38, 0   /* irq 6 */
89        TRAP_HANDLER    39, 0   /* irq 7 */
90        TRAP_HANDLER    40, 0   /* irq 8 */
91        TRAP_HANDLER    41, 0   /* irq 9 */
92        TRAP_HANDLER    42, 0   /* irq 10 */
93        TRAP_HANDLER    43, 0   /* irq 11 */
94        TRAP_HANDLER    44, 0   /* irq 12 */
95        TRAP_HANDLER    45, 0   /* irq 13 */
96        TRAP_HANDLER    46, 0   /* irq 14 */
97        TRAP_HANDLER    47, 0   /* irq 15 */
98
99        .text
100        .code32
101        .align  16
102common_trap:                            /* common trap handler */
103        pushal
104
105        movl    $(DATA_SELECTOR), %eax  /* make sure these are sane */
106        movl    %eax, %ds
107        movl    %eax, %es
108        movl    %eax, %fs
109        movl    %eax, %gs
110        movl    %esp, %ebp
111
112        pushl   %ebp
113        pushl   36(%ebp)
114        pushl   32(%ebp)
115        call    trap                    /* trap(trapno, errno, regs) */
116        addl    $12, %esp
117
118trap_return:
119        popal
120        addl    $8, %esp                /* skip trapno, errno */
121        iret
122        /* NOT REACHED */
123
124
125/*
126 * A world switch to real mode occured. The hypervisor saved the
127 * executing context into "oldctx" and instantiated "newctx", which
128 * gets us here. Here we push a stack frame that is compatible with
129 * a trap frame (see above) so that we can handle this event as a
130 * regular trap.
131 */
132        .text
133        .align  16
134        .globl  switch_to_real_mode
135switch_to_real_mode:
136        pushl   oldctx+VMX_ASSIST_CTX_GS_SEL /* 16 to 32-bit transition */
137        pushl   oldctx+VMX_ASSIST_CTX_FS_SEL
138        pushl   oldctx+VMX_ASSIST_CTX_DS_SEL
139        pushl   oldctx+VMX_ASSIST_CTX_ES_SEL
140        pushl   oldctx+VMX_ASSIST_CTX_SS_SEL
141        pushl   oldctx+VMX_ASSIST_CTX_ESP
142        pushl   oldctx+VMX_ASSIST_CTX_EFLAGS
143        pushl   oldctx+VMX_ASSIST_CTX_CS_SEL
144        pushl   oldctx+VMX_ASSIST_CTX_EIP
145        pushl   $-1                     /* trapno, errno */
146        pushl   $-1
147        pushal
148
149        movl    %esp, %ebp
150        pushl   %ebp
151        call    enter_real_mode
152        addl    $4, %esp
153
154        jmp     trap_return
155        /* NOT REACHED */
156
157
158/*
159 * Switch to protected mode. At this point all the registers have
160 * been reloaded by trap_return and all we have to do is cause a
161 * world switch by turning on CR0.PE.
162 */
163        .text
164        .align  16
165        .globl  switch_to_protected_mode
166switch_to_protected_mode:
167        movl    oldctx+VMX_ASSIST_CTX_CR0, %esp
168        movl    %esp, %cr0              /* actual world switch ! */
169
170        /* NOT REACHED */
171        pushl   $switch_failed
172        call    panic
173        jmp     .
174
175        .data
176        .align  4
177switch_failed:
178        .asciz  "World switch to protected mode failed\n"
179
Note: See TracBrowser for help on using the repository browser.