Diff markup
001 /* Copyright (C) 2004 The KOS Team 001 /* Copyright (C) 2004 The KOS Team
002 Copyright (C) 1999 Free Software Foundatio 002 Copyright (C) 1999 Free Software Foundation, Inc.
003 003
004 This program is free software; you can redi 004 This program is free software; you can redistribute it and/or
005 modify it under the terms of the GNU Genera 005 modify it under the terms of the GNU General Public License
006 as published by the Free Software Foundatio 006 as published by the Free Software Foundation; either version 2
007 of the License, or (at your option) any lat 007 of the License, or (at your option) any later version.
008 008
009 This program is distributed in the hope tha 009 This program is distributed in the hope that it will be useful,
010 but WITHOUT ANY WARRANTY; without even the 010 but WITHOUT ANY WARRANTY; without even the implied warranty of
011 MERCHANTABILITY or FITNESS FOR A PARTICULAR 011 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
012 GNU General Public License for more details 012 GNU General Public License for more details.
013 013
014 You should have received a copy of the GNU 014 You should have received a copy of the GNU General Public License
015 along with this program; if not, write to t 015 along with this program; if not, write to the Free Software
016 Foundation, Inc., 59 Temple Place - Suite 3 016 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307,
017 USA. 017 USA.
018 */ 018 */
019 #include "exception.h" 019 #include "exception.h"
020 020
021 .file "exception_wrappers.S" 021 .file "exception_wrappers.S"
022 022
023 .text 023 .text
024 024
025 /* The address of the table of handlers (defin 025 /* The address of the table of handlers (defined in exception.c) */
026 .extern sos_exception_handler_array 026 .extern sos_exception_handler_array
027 027
028 /* The address of the table of wrappers (defin 028 /* The address of the table of wrappers (defined below, and shared
029 with exception.c */ 029 with exception.c */
030 .globl sos_exception_wrapper_array 030 .globl sos_exception_wrapper_array
031 031
032 032
033 /** 033 /**
034 * For exceptions with/without error code, ref 034 * For exceptions with/without error code, refer to Intel x86 doc vol 3,
035 * section 5.12 035 * section 5.12
036 */ 036 */
037 037
038 /* These wrappers are for exceptions without e 038 /* These wrappers are for exceptions without error code */
039 .irp id, \ 039 .irp id, \
040 SOS_EXCEPT_DIVIDE_ERROR, 040 SOS_EXCEPT_DIVIDE_ERROR, \
041 SOS_EXCEPT_DEBUG, 041 SOS_EXCEPT_DEBUG, \
042 SOS_EXCEPT_NMI_INTERRUPT, 042 SOS_EXCEPT_NMI_INTERRUPT, \
043 SOS_EXCEPT_BREAKPOINT, 043 SOS_EXCEPT_BREAKPOINT, \
044 SOS_EXCEPT_OVERFLOW, 044 SOS_EXCEPT_OVERFLOW, \
045 SOS_EXCEPT_BOUND_RANGE_EXCEDEED, 045 SOS_EXCEPT_BOUND_RANGE_EXCEDEED, \
046 SOS_EXCEPT_INVALID_OPCODE, 046 SOS_EXCEPT_INVALID_OPCODE, \
047 SOS_EXCEPT_DEVICE_NOT_AVAILABLE, 047 SOS_EXCEPT_DEVICE_NOT_AVAILABLE, \
048 SOS_EXCEPT_COPROCESSOR_SEGMENT_OVERRU 048 SOS_EXCEPT_COPROCESSOR_SEGMENT_OVERRUN, \
049 SOS_EXCEPT_INTEL_RESERVED_1, 049 SOS_EXCEPT_INTEL_RESERVED_1, \
050 SOS_EXCEPT_FLOATING_POINT_ERROR, 050 SOS_EXCEPT_FLOATING_POINT_ERROR, \
051 SOS_EXCEPT_MACHINE_CHECK, 051 SOS_EXCEPT_MACHINE_CHECK, \
052 SOS_EXCEPT_INTEL_RESERVED_2, 052 SOS_EXCEPT_INTEL_RESERVED_2, \
053 SOS_EXCEPT_INTEL_RESERVED_3, 053 SOS_EXCEPT_INTEL_RESERVED_3, \
054 SOS_EXCEPT_INTEL_RESERVED_4, 054 SOS_EXCEPT_INTEL_RESERVED_4, \
055 SOS_EXCEPT_INTEL_RESERVED_5, 055 SOS_EXCEPT_INTEL_RESERVED_5, \
056 SOS_EXCEPT_INTEL_RESERVED_6, 056 SOS_EXCEPT_INTEL_RESERVED_6, \
057 SOS_EXCEPT_INTEL_RESERVED_7, 057 SOS_EXCEPT_INTEL_RESERVED_7, \
058 SOS_EXCEPT_INTEL_RESERVED_8, 058 SOS_EXCEPT_INTEL_RESERVED_8, \
059 SOS_EXCEPT_INTEL_RESERVED_9, 059 SOS_EXCEPT_INTEL_RESERVED_9, \
060 SOS_EXCEPT_INTEL_RESERVED_10, 060 SOS_EXCEPT_INTEL_RESERVED_10, \
061 SOS_EXCEPT_INTEL_RESERVED_11, 061 SOS_EXCEPT_INTEL_RESERVED_11, \
062 SOS_EXCEPT_INTEL_RESERVED_12, 062 SOS_EXCEPT_INTEL_RESERVED_12, \
063 SOS_EXCEPT_INTEL_RESERVED_13, 063 SOS_EXCEPT_INTEL_RESERVED_13, \
064 SOS_EXCEPT_INTEL_RESERVED_14 064 SOS_EXCEPT_INTEL_RESERVED_14
065 065
066 .p2align 2, 0x90 066 .p2align 2, 0x90
067 sos_exception_wrapper_\id: 067 sos_exception_wrapper_\id:
068 .type sos_exception_wrapper_\id,@funct 068 .type sos_exception_wrapper_\id,@function
069 069
070 /* Fake error code */ 070 /* Fake error code */
071 pushl $0 071 pushl $0
072 /* Backup the context */ 072 /* Backup the context */
073 pushl %ebp 073 pushl %ebp
074 movl %esp, %ebp 074 movl %esp, %ebp
075 075
076 pushl %edi 076 pushl %edi
077 pushl %esi 077 pushl %esi
078 pushl %edx 078 pushl %edx
079 pushl %ecx 079 pushl %ecx
080 pushl %ebx 080 pushl %ebx
081 pushl %eax 081 pushl %eax
082 subl $2,%esp 082 subl $2,%esp
083 pushw %ss 083 pushw %ss
084 pushw %ds 084 pushw %ds
085 pushw %es 085 pushw %es
086 pushw %fs 086 pushw %fs
087 pushw %gs 087 pushw %gs
088 088
089 /* Call the handler with excep 089 /* Call the handler with exception number as
090 * argument */ 090 * argument */
091 pushl $\id 091 pushl $\id
092 leal sos_exception_handler_ar 092 leal sos_exception_handler_array,%edi
093 call *\id*4(%edi) 093 call *\id*4(%edi)
094 addl $4, %esp 094 addl $4, %esp
095 095
096 /* Restore the context */ 096 /* Restore the context */
097 popw %gs 097 popw %gs
098 popw %fs 098 popw %fs
099 popw %es 099 popw %es
100 popw %ds 100 popw %ds
101 popw %ss 101 popw %ss
102 addl $2,%esp 102 addl $2,%esp
103 popl %eax 103 popl %eax
104 popl %ebx 104 popl %ebx
105 popl %ecx 105 popl %ecx
106 popl %edx 106 popl %edx
107 popl %esi 107 popl %esi
108 popl %edi 108 popl %edi
109 109
110 popl %ebp 110 popl %ebp
111 /* Remove fake error code */ 111 /* Remove fake error code */
112 addl $4, %esp 112 addl $4, %esp
113 iret 113 iret
114 .endr 114 .endr
115 115
116 /* These wrappers are for exceptions w 116 /* These wrappers are for exceptions with error code */
117 .irp id, \ 117 .irp id, \
118 SOS_EXCEPT_INVALID_TSS, 118 SOS_EXCEPT_INVALID_TSS, \
119 SOS_EXCEPT_SEGMENT_NOT_PRESENT, 119 SOS_EXCEPT_SEGMENT_NOT_PRESENT, \
120 SOS_EXCEPT_STACK_SEGMENT_FAULT, 120 SOS_EXCEPT_STACK_SEGMENT_FAULT, \
121 SOS_EXCEPT_GENERAL_PROTECTION, 121 SOS_EXCEPT_GENERAL_PROTECTION, \
122 SOS_EXCEPT_PAGE_FAULT, 122 SOS_EXCEPT_PAGE_FAULT, \
123 SOS_EXCEPT_ALIGNEMENT_CHECK 123 SOS_EXCEPT_ALIGNEMENT_CHECK
124 124
125 .p2align 2, 0x90 125 .p2align 2, 0x90
126 sos_exception_wrapper_\id: 126 sos_exception_wrapper_\id:
127 .type sos_exception_wrapper_\id,@funct 127 .type sos_exception_wrapper_\id,@function
128 128
129 /* ret eflags */ 129 /* ret eflags */
130 /* ret cs */ 130 /* ret cs */
131 /* ret eip */ 131 /* ret eip */
132 /* Error code */ 132 /* Error code */
133 133
134 /* Backup the context */ 134 /* Backup the context */
135 pushl %ebp 135 pushl %ebp
136 movl %esp, %ebp 136 movl %esp, %ebp
137 137
138 pushl %edi 138 pushl %edi
139 pushl %esi 139 pushl %esi
140 pushl %edx 140 pushl %edx
141 pushl %ecx 141 pushl %ecx
142 pushl %ebx 142 pushl %ebx
143 pushl %eax 143 pushl %eax
144 subl $2,%esp 144 subl $2,%esp
145 pushw %ss 145 pushw %ss
146 pushw %ds 146 pushw %ds
147 pushw %es 147 pushw %es
148 pushw %fs 148 pushw %fs
149 pushw %gs 149 pushw %gs
150 150
151 /* Call the handler with excep 151 /* Call the handler with exception number as
152 * argument */ 152 * argument */
153 pushl $\id 153 pushl $\id
154 leal sos_exception_handler_ar 154 leal sos_exception_handler_array,%edi
155 call *\id*4(%edi) 155 call *\id*4(%edi)
156 addl $4, %esp 156 addl $4, %esp
157 157
158 /* Restore the context */ 158 /* Restore the context */
159 popw %gs 159 popw %gs
160 popw %fs 160 popw %fs
161 popw %es 161 popw %es
162 popw %ds 162 popw %ds
163 popw %ss 163 popw %ss
164 addl $2,%esp 164 addl $2,%esp
165 popl %eax 165 popl %eax
166 popl %ebx 166 popl %ebx
167 popl %ecx 167 popl %ecx
168 popl %edx 168 popl %edx
169 popl %esi 169 popl %esi
170 popl %edi 170 popl %edi
171 popl %ebp 171 popl %ebp
172 172
173 /* Error code isn't compatible 173 /* Error code isn't compatible with iretd */
174 addl $4, %esp 174 addl $4, %esp
175 175
176 iret 176 iret
177 .endr 177 .endr
178 178
179 179
180 /* Double fault handler not supported. We must 180 /* Double fault handler not supported. We must define it since we
181 define an entry for it in the sos_exception 181 define an entry for it in the sos_exception_wrapper_array. */
182 .irp id, SOS_EXCEPT_DOUBLE_FAULT 182 .irp id, SOS_EXCEPT_DOUBLE_FAULT
183 .p2align 2, 0x90 183 .p2align 2, 0x90
184 sos_exception_wrapper_\id: 184 sos_exception_wrapper_\id:
185 .type sos_exception_wrapper_\id,@function 185 .type sos_exception_wrapper_\id,@function
186 1: hlt 186 1: hlt
187 jmp 1b /* Machine halting */ 187 jmp 1b /* Machine halting */
188 .endr 188 .endr
189 189
190 /* Build the sos_irq_wrapper_array, shared wit 190 /* Build the sos_irq_wrapper_array, shared with interrupt.c */
191 .section ".rodata" 191 .section ".rodata"
192 .p2align 5, 0x0 192 .p2align 5, 0x0
193 sos_exception_wrapper_array: 193 sos_exception_wrapper_array:
194 .irp id, 0,1,2,3,4,5,6,7,8,9,10,11,12, 194 .irp id, 0,1,2,3,4,5,6,7,8,9,10,11,12,13,14,15, \
195 16,17,18,19,20,21,22,23,24,25 195 16,17,18,19,20,21,22,23,24,25,26,27,29,30,31
196 .long (sos_exception_wrapper_\id) 196 .long (sos_exception_wrapper_\id)
197 .endr 197 .endr