1 #------------------------------------------------------------------------------
3 #* Copyright 2006 - 2009, Intel Corporation
4 #* All rights reserved. This program and the accompanying materials
5 #* are licensed and made available under the terms and conditions of the BSD License
6 #* which accompanies this distribution. The full text of the license may be found at
7 #* http://opensource.org/licenses/bsd-license.php
9 #* THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
10 #* WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
16 #------------------------------------------------------------------------------
22 #EXTRN ASM_PFX(mErrorCodeFlag):DWORD # Error code flags for exceptions
26 # point to the external interrupt vector table
28 ExternalVectorTablePtr:
31 ASM_GLOBAL ASM_PFX(InitializeExternalVectorTablePtr)
32 ASM_PFX(InitializeExternalVectorTablePtr):
34 movl %eax, ExternalVectorTablePtr
37 #------------------------------------------------------------------------------
42 #------------------------------------------------------------------------------
43 ASM_GLOBAL ASM_PFX(SetCodeSelector)
44 ASM_PFX(SetCodeSelector):
47 leal setCodeSelectorLongJump, %eax
50 .byte 0xFF, 0x2C, 0x24 # jmp *(%esp) note:(FWORD jmp)
51 setCodeSelectorLongJump:
55 #------------------------------------------------------------------------------
60 #------------------------------------------------------------------------------
61 ASM_GLOBAL ASM_PFX(SetDataSelectors)
62 ASM_PFX(SetDataSelectors):
71 #---------------------------------------;
72 # CommonInterruptEntry ;
73 #---------------------------------------;
74 # The follow algorithm is used for the common interrupt routine.
76 ASM_GLOBAL ASM_PFX(CommonInterruptEntry)
77 ASM_PFX(CommonInterruptEntry):
80 # All interrupt handlers are invoked through interrupt gates, so
81 # IF flag automatically cleared at the entry point
85 # Calculate vector number
87 # Get the return address of call, actually, it is the
88 # address of vector number.
93 cmpl $32, %ecx # Intel reserved vector for exceptions?
95 bt %ecx, ASM_PFX(mErrorCodeFlag)
102 # +---------------------+
104 # +---------------------+
106 # +---------------------+
108 # +---------------------+
110 # +---------------------+ <-- ESP
113 # ECX - Vector Number
117 # Put Vector Number on stack
122 # Put 0 (dummy) error code on stack, and restore ECX
124 xorl %ecx, %ecx # ECX = 0
127 jmp ErrorCodeAndVectorOnStack
133 # +---------------------+
135 # +---------------------+
137 # +---------------------+
139 # +---------------------+
141 # +---------------------+
143 # +---------------------+ <-- ESP
146 # ECX - Vector Number
150 # Put Vector Number on stack and restore ECX
155 # Fall through to join main routine code
156 # at ErrorCodeAndVectorOnStack
158 CommonInterruptEntry_al_0000:
159 jmp CommonInterruptEntry_al_0000
161 ErrorCodeAndVectorOnStack:
167 # +---------------------+
169 # +---------------------+
171 # +---------------------+
173 # +---------------------+
175 # +---------------------+
177 # +---------------------+
179 # +---------------------+ <-- EBP
183 # Align stack to make sure that EFI_FX_SAVE_STATE_IA32 of EFI_SYSTEM_CONTEXT_IA32
186 andl $0x0fffffff0, %esp
189 #; UINT32 Edi, Esi, Ebp, Esp, Ebx, Edx, Ecx, Eax;
200 #; UINT32 Gs, Fs, Es, Ds, Cs, Ss;
203 movzwl 16(%ebp), %eax
218 #; UINT32 Gdtr[2], Idtr[2];
244 #; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4;
258 #; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7;
261 #; clear Dr7 while executing debugger itself
267 #; insure all status bits in dr6 are clear...
280 #; FX_SAVE_STATE_IA32 FxSaveState;
283 .byte 0x0f, 0x0ae, 0x07 #fxsave [edi]
285 #; UINT32 ExceptionData;
288 #; call into exception handler
289 movl ExternalVectorTablePtr, %eax # get the interrupt vectors base
290 orl %eax, %eax # NULL?
291 jz nullExternalExceptionHandler
294 movl (%eax,%ecx,4), %eax
295 orl %eax, %eax # NULL?
296 jz nullExternalExceptionHandler
298 #; Prepare parameter and call
305 # Call External Exception Handler
310 nullExternalExceptionHandler:
313 #; UINT32 ExceptionData;
316 #; FX_SAVE_STATE_IA32 FxSaveState;
318 .byte 0x0f, 0x0ae, 0x0e # fxrstor [esi]
321 #; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7;
330 #; skip restore of dr6. We cleared dr6 during the context save.
335 #; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4;
338 addl $4, %esp # not for Cr1
350 #; UINT32 Gdtr[2], Idtr[2];
351 #; Best not let anyone mess with these particular registers...
357 #; UINT32 Gs, Fs, Es, Ds, Cs, Ss;
358 #; NOTE - modified segment registers could hang the debugger... We
359 #; could attempt to insulate ourselves against this possibility,
360 #; but that poses risks as well.
369 #; UINT32 Edi, Esi, Ebp, Esp, Ebx, Edx, Ecx, Eax;
372 addl $4, %esp # not for ebp
373 addl $4, %esp # not for esp