]> git.proxmox.com Git - mirror_edk2.git/blob - UefiCpuPkg/Library/CpuExceptionHandlerLib/Ia32/ExceptionHandlerAsm.asm
Remove CPU dead loop code from IA32 assembly codes.
[mirror_edk2.git] / UefiCpuPkg / Library / CpuExceptionHandlerLib / Ia32 / ExceptionHandlerAsm.asm
1 ;------------------------------------------------------------------------------ ;
2 ; Copyright (c) 2012, Intel Corporation. All rights reserved.<BR>
3 ; This program and the accompanying materials
4 ; are licensed and made available under the terms and conditions of the BSD License
5 ; which accompanies this distribution. The full text of the license may be found at
6 ; http://opensource.org/licenses/bsd-license.php.
7 ;
8 ; THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
9 ; WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
10 ;
11 ; Module Name:
12 ;
13 ; ExceptionHandlerAsm.Asm
14 ;
15 ; Abstract:
16 ;
17 ; IA32 CPU Exception Handler
18 ;
19 ; Notes:
20 ;
21 ;------------------------------------------------------------------------------
22
23 .686
24 .model flat,C
25
26 ;
27 ; CommonExceptionHandler()
28 ;
29 CommonExceptionHandler PROTO C
30
31 .data
32
33 CommonEntryAddr DD CommonInterruptEntry
34
35 EXTRN mErrorCodeFlag:DWORD ; Error code flags for exceptions
36
37 .code
38
39 ;
40 ; exception handler stub table
41 ;
42 Exception0Handle:
43 push 0
44 jmp dword ptr [CommonEntryAddr]
45 Exception1Handle:
46 push 1
47 jmp dword ptr [CommonEntryAddr]
48 Exception2Handle:
49 push 2
50 jmp dword ptr [CommonEntryAddr]
51 Exception3Handle:
52 push 3
53 jmp dword ptr [CommonEntryAddr]
54 Exception4Handle:
55 push 4
56 jmp dword ptr [CommonEntryAddr]
57 Exception5Handle:
58 push 5
59 jmp dword ptr [CommonEntryAddr]
60 Exception6Handle:
61 push 6
62 jmp dword ptr [CommonEntryAddr]
63 Exception7Handle:
64 push 7
65 jmp dword ptr [CommonEntryAddr]
66 Exception8Handle:
67 push 8
68 jmp dword ptr [CommonEntryAddr]
69 Exception9Handle:
70 push 9
71 jmp dword ptr [CommonEntryAddr]
72 Exception10Handle:
73 push 10
74 jmp dword ptr [CommonEntryAddr]
75 Exception11Handle:
76 push 11
77 jmp dword ptr [CommonEntryAddr]
78 Exception12Handle:
79 push 12
80 jmp dword ptr [CommonEntryAddr]
81 Exception13Handle:
82 push 13
83 jmp dword ptr [CommonEntryAddr]
84 Exception14Handle:
85 push 14
86 jmp dword ptr [CommonEntryAddr]
87 Exception15Handle:
88 push 15
89 jmp dword ptr [CommonEntryAddr]
90 Exception16Handle:
91 push 16
92 jmp dword ptr [CommonEntryAddr]
93 Exception17Handle:
94 push 17
95 jmp dword ptr [CommonEntryAddr]
96 Exception18Handle:
97 push 18
98 jmp dword ptr [CommonEntryAddr]
99 Exception19Handle:
100 push 19
101 jmp dword ptr [CommonEntryAddr]
102 Exception20Handle:
103 push 20
104 jmp dword ptr [CommonEntryAddr]
105 Exception21Handle:
106 push 21
107 jmp dword ptr [CommonEntryAddr]
108 Exception22Handle:
109 push 22
110 jmp dword ptr [CommonEntryAddr]
111 Exception23Handle:
112 push 23
113 jmp dword ptr [CommonEntryAddr]
114 Exception24Handle:
115 push 24
116 jmp dword ptr [CommonEntryAddr]
117 Exception25Handle:
118 push 25
119 jmp dword ptr [CommonEntryAddr]
120 Exception26Handle:
121 push 26
122 jmp dword ptr [CommonEntryAddr]
123 Exception27Handle:
124 push 27
125 jmp dword ptr [CommonEntryAddr]
126 Exception28Handle:
127 push 28
128 jmp dword ptr [CommonEntryAddr]
129 Exception29Handle:
130 push 29
131 jmp dword ptr [CommonEntryAddr]
132 Exception30Handle:
133 push 30
134 jmp dword ptr [CommonEntryAddr]
135 Exception31Handle:
136 push 31
137 jmp dword ptr [CommonEntryAddr]
138
139 ;----------------------------------------------------------------------------;
140 ; CommonInterruptEntry ;
141 ;----------------------------------------------------------------------------;
142 ; The follow algorithm is used for the common interrupt routine.
143 ; Entry from each interrupt with a push eax and eax=interrupt number
144
145 CommonInterruptEntry PROC PUBLIC
146 cli
147 ;
148 ; All interrupt handlers are invoked through interrupt gates, so
149 ; IF flag automatically cleared at the entry point
150 ;
151
152 ;
153 ; Calculate vector number
154 ;
155 ; Get the return address of call, actually, it is the
156 ; address of vector number.
157 ;
158 xchg ecx, [esp]
159 and ecx, 0FFFFh
160 cmp ecx, 32 ; Intel reserved vector for exceptions?
161 jae NoErrorCode
162 bt mErrorCodeFlag, ecx
163 jc HasErrorCode
164
165 NoErrorCode:
166
167 ;
168 ; Stack:
169 ; +---------------------+
170 ; + EFlags +
171 ; +---------------------+
172 ; + CS +
173 ; +---------------------+
174 ; + EIP +
175 ; +---------------------+
176 ; + ECX +
177 ; +---------------------+ <-- ESP
178 ;
179 ; Registers:
180 ; ECX - Vector Number
181 ;
182
183 ;
184 ; Put Vector Number on stack
185 ;
186 push ecx
187
188 ;
189 ; Put 0 (dummy) error code on stack, and restore ECX
190 ;
191 xor ecx, ecx ; ECX = 0
192 xchg ecx, [esp+4]
193
194 jmp ErrorCodeAndVectorOnStack
195
196 HasErrorCode:
197
198 ;
199 ; Stack:
200 ; +---------------------+
201 ; + EFlags +
202 ; +---------------------+
203 ; + CS +
204 ; +---------------------+
205 ; + EIP +
206 ; +---------------------+
207 ; + Error Code +
208 ; +---------------------+
209 ; + ECX +
210 ; +---------------------+ <-- ESP
211 ;
212 ; Registers:
213 ; ECX - Vector Number
214 ;
215
216 ;
217 ; Put Vector Number on stack and restore ECX
218 ;
219 xchg ecx, [esp]
220
221 ErrorCodeAndVectorOnStack:
222 push ebp
223 mov ebp, esp
224
225 ;
226 ; Stack:
227 ; +---------------------+
228 ; + EFlags +
229 ; +---------------------+
230 ; + CS +
231 ; +---------------------+
232 ; + EIP +
233 ; +---------------------+
234 ; + Error Code +
235 ; +---------------------+
236 ; + Vector Number +
237 ; +---------------------+
238 ; + EBP +
239 ; +---------------------+ <-- EBP
240 ;
241
242 ;
243 ; Align stack to make sure that EFI_FX_SAVE_STATE_IA32 of EFI_SYSTEM_CONTEXT_IA32
244 ; is 16-byte aligned
245 ;
246 and esp, 0fffffff0h
247 sub esp, 12
248
249 ;; UINT32 Edi, Esi, Ebp, Esp, Ebx, Edx, Ecx, Eax;
250 push eax
251 push ecx
252 push edx
253 push ebx
254 lea ecx, [ebp + 6 * 4]
255 push ecx ; ESP
256 push dword ptr [ebp] ; EBP
257 push esi
258 push edi
259
260 ;; UINT32 Gs, Fs, Es, Ds, Cs, Ss;
261 mov eax, ss
262 push eax
263 movzx eax, word ptr [ebp + 4 * 4]
264 push eax
265 mov eax, ds
266 push eax
267 mov eax, es
268 push eax
269 mov eax, fs
270 push eax
271 mov eax, gs
272 push eax
273
274 ;; UINT32 Eip;
275 mov eax, [ebp + 3 * 4]
276 push eax
277
278 ;; UINT32 Gdtr[2], Idtr[2];
279 sub esp, 8
280 sidt [esp]
281 mov eax, [esp + 2]
282 xchg eax, [esp]
283 and eax, 0FFFFh
284 mov [esp+4], eax
285
286 sub esp, 8
287 sgdt [esp]
288 mov eax, [esp + 2]
289 xchg eax, [esp]
290 and eax, 0FFFFh
291 mov [esp+4], eax
292
293 ;; UINT32 Ldtr, Tr;
294 xor eax, eax
295 str ax
296 push eax
297 sldt ax
298 push eax
299
300 ;; UINT32 EFlags;
301 mov eax, [ebp + 5 * 4]
302 push eax
303
304 ;; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4;
305 mov eax, cr4
306 or eax, 208h
307 mov cr4, eax
308 push eax
309 mov eax, cr3
310 push eax
311 mov eax, cr2
312 push eax
313 xor eax, eax
314 push eax
315 mov eax, cr0
316 push eax
317
318 ;; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7;
319 mov eax, dr7
320 push eax
321 mov eax, dr6
322 push eax
323 mov eax, dr3
324 push eax
325 mov eax, dr2
326 push eax
327 mov eax, dr1
328 push eax
329 mov eax, dr0
330 push eax
331
332 ;; FX_SAVE_STATE_IA32 FxSaveState;
333 sub esp, 512
334 mov edi, esp
335 db 0fh, 0aeh, 07h ;fxsave [edi]
336
337 ;; UEFI calling convention for IA32 requires that Direction flag in EFLAGs is clear
338 cld
339
340 ;; UINT32 ExceptionData;
341 push dword ptr [ebp + 2 * 4]
342
343 ;; Prepare parameter and call
344 mov edx, esp
345 push edx
346 mov edx, dword ptr [ebp + 1 * 4]
347 push edx
348
349 ;
350 ; Call External Exception Handler
351 ;
352 mov eax, CommonExceptionHandler
353 call eax
354 add esp, 8
355
356 cli
357 ;; UINT32 ExceptionData;
358 add esp, 4
359
360 ;; FX_SAVE_STATE_IA32 FxSaveState;
361 mov esi, esp
362 db 0fh, 0aeh, 0eh ; fxrstor [esi]
363 add esp, 512
364
365 ;; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7;
366 ;; Skip restoration of DRx registers to support in-circuit emualators
367 ;; or debuggers set breakpoint in interrupt/exception context
368 add esp, 4 * 6
369
370 ;; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4;
371 pop eax
372 mov cr0, eax
373 add esp, 4 ; not for Cr1
374 pop eax
375 mov cr2, eax
376 pop eax
377 mov cr3, eax
378 pop eax
379 mov cr4, eax
380
381 ;; UINT32 EFlags;
382 pop dword ptr [ebp + 5 * 4]
383
384 ;; UINT32 Ldtr, Tr;
385 ;; UINT32 Gdtr[2], Idtr[2];
386 ;; Best not let anyone mess with these particular registers...
387 add esp, 24
388
389 ;; UINT32 Eip;
390 pop dword ptr [ebp + 3 * 4]
391
392 ;; UINT32 Gs, Fs, Es, Ds, Cs, Ss;
393 ;; NOTE - modified segment registers could hang the debugger... We
394 ;; could attempt to insulate ourselves against this possibility,
395 ;; but that poses risks as well.
396 ;;
397 pop gs
398 pop fs
399 pop es
400 pop ds
401 pop dword ptr [ebp + 4 * 4]
402 pop ss
403
404 ;; UINT32 Edi, Esi, Ebp, Esp, Ebx, Edx, Ecx, Eax;
405 pop edi
406 pop esi
407 add esp, 4 ; not for ebp
408 add esp, 4 ; not for esp
409 pop ebx
410 pop edx
411 pop ecx
412 pop eax
413
414 mov esp, ebp
415 pop ebp
416 add esp, 8
417 iretd
418
419 CommonInterruptEntry ENDP
420
421 ;---------------------------------------;
422 ; _GetTemplateAddressMap ;
423 ;----------------------------------------------------------------------------;
424 ;
425 ; Protocol prototype
426 ; GetTemplateAddressMap (
427 ; EXCEPTION_HANDLER_TEMPLATE_MAP *AddressMap
428 ; );
429 ;
430 ; Routine Description:
431 ;
432 ; Return address map of interrupt handler template so that C code can generate
433 ; interrupt table.
434 ;
435 ; Arguments:
436 ;
437 ;
438 ; Returns:
439 ;
440 ; Nothing
441 ;
442 ;
443 ; Input: [ebp][0] = Original ebp
444 ; [ebp][4] = Return address
445 ;
446 ; Output: Nothing
447 ;
448 ; Destroys: Nothing
449 ;-----------------------------------------------------------------------------;
450 GetTemplateAddressMap proc near public
451 push ebp ; C prolog
452 mov ebp, esp
453 pushad
454
455 mov ebx, dword ptr [ebp+08h]
456 mov dword ptr [ebx], Exception0Handle
457 mov dword ptr [ebx+4h], Exception1Handle - Exception0Handle
458
459 popad
460 pop ebp
461 ret
462 GetTemplateAddressMap ENDP
463
464 END