]> git.proxmox.com Git - mirror_edk2.git/blob - UefiCpuPkg/CpuDxe/Ia32/CpuAsm.asm
Remove svn:executable on *.c, *.h, *.asm, *.S, *.inf and *.asl*
[mirror_edk2.git] / UefiCpuPkg / CpuDxe / Ia32 / CpuAsm.asm
1 TITLE CpuAsm.asm:
2 ;------------------------------------------------------------------------------
3 ;*
4 ;* Copyright 2006 - 2009, Intel Corporation
5 ;* All rights reserved. This program and the accompanying materials
6 ;* are licensed and made available under the terms and conditions of the BSD License
7 ;* which accompanies this distribution. The full text of the license may be found at
8 ;* http://opensource.org/licenses/bsd-license.php
9 ;*
10 ;* THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS,
11 ;* WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED.
12 ;*
13 ;* CpuAsm.asm
14 ;*
15 ;* Abstract:
16 ;*
17 ;------------------------------------------------------------------------------
18
19 .686
20 .model flat,C
21 .code
22
23 EXTRN mErrorCodeFlag:DWORD ; Error code flags for exceptions
24
25 ;
26 ; point to the external interrupt vector table
27 ;
28 ExternalVectorTablePtr DWORD 0
29
30 InitializeExternalVectorTablePtr PROC PUBLIC
31 mov eax, [esp+4]
32 mov ExternalVectorTablePtr, eax
33 ret
34 InitializeExternalVectorTablePtr ENDP
35
36 ;------------------------------------------------------------------------------
37 ; VOID
38 ; SetCodeSelector (
39 ; UINT16 Selector
40 ; );
41 ;------------------------------------------------------------------------------
42 SetCodeSelector PROC PUBLIC
43 mov ecx, [esp+4]
44 sub esp, 0x10
45 lea eax, setCodeSelectorLongJump
46 mov [esp], eax
47 mov [esp+4], cx
48 jmp fword ptr [esp]
49 setCodeSelectorLongJump:
50 add esp, 0x10
51 ret
52 SetCodeSelector ENDP
53
54 ;------------------------------------------------------------------------------
55 ; VOID
56 ; SetDataSelectors (
57 ; UINT16 Selector
58 ; );
59 ;------------------------------------------------------------------------------
60 SetDataSelectors PROC PUBLIC
61 mov ecx, [esp+4]
62 mov ss, cx
63 mov ds, cx
64 mov es, cx
65 mov fs, cx
66 mov gs, cx
67 ret
68 SetDataSelectors ENDP
69
70 ;---------------------------------------;
71 ; CommonInterruptEntry ;
72 ;---------------------------------------;
73 ; The follow algorithm is used for the common interrupt routine.
74
75 CommonInterruptEntry PROC PUBLIC
76 cli
77 ;
78 ; All interrupt handlers are invoked through interrupt gates, so
79 ; IF flag automatically cleared at the entry point
80 ;
81
82 ;
83 ; Calculate vector number
84 ;
85 ; Get the return address of call, actually, it is the
86 ; address of vector number.
87 ;
88 xchg ecx, [esp]
89 mov cx, [ecx]
90 and ecx, 0FFFFh
91 cmp ecx, 32 ; Intel reserved vector for exceptions?
92 jae NoErrorCode
93 bt mErrorCodeFlag, ecx
94 jc HasErrorCode
95
96 NoErrorCode:
97
98 ;
99 ; Stack:
100 ; +---------------------+
101 ; + EFlags +
102 ; +---------------------+
103 ; + CS +
104 ; +---------------------+
105 ; + EIP +
106 ; +---------------------+
107 ; + ECX +
108 ; +---------------------+ <-- ESP
109 ;
110 ; Registers:
111 ; ECX - Vector Number
112 ;
113
114 ;
115 ; Put Vector Number on stack
116 ;
117 push ecx
118
119 ;
120 ; Put 0 (dummy) error code on stack, and restore ECX
121 ;
122 xor ecx, ecx ; ECX = 0
123 xchg ecx, [esp+4]
124
125 jmp ErrorCodeAndVectorOnStack
126
127 HasErrorCode:
128
129 ;
130 ; Stack:
131 ; +---------------------+
132 ; + EFlags +
133 ; +---------------------+
134 ; + CS +
135 ; +---------------------+
136 ; + EIP +
137 ; +---------------------+
138 ; + Error Code +
139 ; +---------------------+
140 ; + ECX +
141 ; +---------------------+ <-- ESP
142 ;
143 ; Registers:
144 ; ECX - Vector Number
145 ;
146
147 ;
148 ; Put Vector Number on stack and restore ECX
149 ;
150 xchg ecx, [esp]
151
152 ;
153 ; Fall through to join main routine code
154 ; at ErrorCodeAndVectorOnStack
155 ;
156 @@:
157 jmp @B
158
159 ErrorCodeAndVectorOnStack:
160 push ebp
161 mov ebp, esp
162
163 ;
164 ; Stack:
165 ; +---------------------+
166 ; + EFlags +
167 ; +---------------------+
168 ; + CS +
169 ; +---------------------+
170 ; + EIP +
171 ; +---------------------+
172 ; + Error Code +
173 ; +---------------------+
174 ; + Vector Number +
175 ; +---------------------+
176 ; + EBP +
177 ; +---------------------+ <-- EBP
178 ;
179
180 ;
181 ; Align stack to make sure that EFI_FX_SAVE_STATE_IA32 of EFI_SYSTEM_CONTEXT_IA32
182 ; is 16-byte aligned
183 ;
184 and esp, 0fffffff0h
185 sub esp, 12
186
187 ;; UINT32 Edi, Esi, Ebp, Esp, Ebx, Edx, Ecx, Eax;
188 push eax
189 push ecx
190 push edx
191 push ebx
192 lea ecx, [ebp + 6 * 4]
193 push ecx ; ESP
194 push dword ptr [ebp] ; EBP
195 push esi
196 push edi
197
198 ;; UINT32 Gs, Fs, Es, Ds, Cs, Ss;
199 mov eax, ss
200 push eax
201 movzx eax, word ptr [ebp + 4 * 4]
202 push eax
203 mov eax, ds
204 push eax
205 mov eax, es
206 push eax
207 mov eax, fs
208 push eax
209 mov eax, gs
210 push eax
211
212 ;; UINT32 Eip;
213 mov eax, [ebp + 3 * 4]
214 push eax
215
216 ;; UINT32 Gdtr[2], Idtr[2];
217 sub esp, 8
218 sidt [esp]
219 mov eax, [esp + 2]
220 xchg eax, [esp]
221 and eax, 0FFFFh
222 mov [esp+4], eax
223
224 sub esp, 8
225 sgdt [esp]
226 mov eax, [esp + 2]
227 xchg eax, [esp]
228 and eax, 0FFFFh
229 mov [esp+4], eax
230
231 ;; UINT32 Ldtr, Tr;
232 xor eax, eax
233 str ax
234 push eax
235 sldt ax
236 push eax
237
238 ;; UINT32 EFlags;
239 mov eax, [ebp + 5 * 4]
240 push eax
241
242 ;; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4;
243 mov eax, cr4
244 or eax, 208h
245 mov cr4, eax
246 push eax
247 mov eax, cr3
248 push eax
249 mov eax, cr2
250 push eax
251 xor eax, eax
252 push eax
253 mov eax, cr0
254 push eax
255
256 ;; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7;
257 mov eax, dr7
258 push eax
259 ;; clear Dr7 while executing debugger itself
260 xor eax, eax
261 mov dr7, eax
262
263 mov eax, dr6
264 push eax
265 ;; insure all status bits in dr6 are clear...
266 xor eax, eax
267 mov dr6, eax
268
269 mov eax, dr3
270 push eax
271 mov eax, dr2
272 push eax
273 mov eax, dr1
274 push eax
275 mov eax, dr0
276 push eax
277
278 ;; FX_SAVE_STATE_IA32 FxSaveState;
279 sub esp, 512
280 mov edi, esp
281 db 0fh, 0aeh, 07h ;fxsave [edi]
282
283 ;; UINT32 ExceptionData;
284 push dword ptr [ebp + 2 * 4]
285
286 ;; call into exception handler
287 mov eax, ExternalVectorTablePtr ; get the interrupt vectors base
288 or eax, eax ; NULL?
289 jz nullExternalExceptionHandler
290
291 mov ecx, [ebp + 4]
292 mov eax, [eax + ecx * 4]
293 or eax, eax ; NULL?
294 jz nullExternalExceptionHandler
295
296 ;; Prepare parameter and call
297 mov edx, esp
298 push edx
299 mov edx, dword ptr [ebp + 1 * 4]
300 push edx
301
302 ;
303 ; Call External Exception Handler
304 ;
305 call eax
306 add esp, 8
307
308 nullExternalExceptionHandler:
309
310 cli
311 ;; UINT32 ExceptionData;
312 add esp, 4
313
314 ;; FX_SAVE_STATE_IA32 FxSaveState;
315 mov esi, esp
316 db 0fh, 0aeh, 0eh ; fxrstor [esi]
317 add esp, 512
318
319 ;; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7;
320 pop eax
321 mov dr0, eax
322 pop eax
323 mov dr1, eax
324 pop eax
325 mov dr2, eax
326 pop eax
327 mov dr3, eax
328 ;; skip restore of dr6. We cleared dr6 during the context save.
329 add esp, 4
330 pop eax
331 mov dr7, eax
332
333 ;; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4;
334 pop eax
335 mov cr0, eax
336 add esp, 4 ; not for Cr1
337 pop eax
338 mov cr2, eax
339 pop eax
340 mov cr3, eax
341 pop eax
342 mov cr4, eax
343
344 ;; UINT32 EFlags;
345 pop dword ptr [ebp + 5 * 4]
346
347 ;; UINT32 Ldtr, Tr;
348 ;; UINT32 Gdtr[2], Idtr[2];
349 ;; Best not let anyone mess with these particular registers...
350 add esp, 24
351
352 ;; UINT32 Eip;
353 pop dword ptr [ebp + 3 * 4]
354
355 ;; UINT32 Gs, Fs, Es, Ds, Cs, Ss;
356 ;; NOTE - modified segment registers could hang the debugger... We
357 ;; could attempt to insulate ourselves against this possibility,
358 ;; but that poses risks as well.
359 ;;
360 pop gs
361 pop fs
362 pop es
363 pop ds
364 pop dword ptr [ebp + 4 * 4]
365 pop ss
366
367 ;; UINT32 Edi, Esi, Ebp, Esp, Ebx, Edx, Ecx, Eax;
368 pop edi
369 pop esi
370 add esp, 4 ; not for ebp
371 add esp, 4 ; not for esp
372 pop ebx
373 pop edx
374 pop ecx
375 pop eax
376
377 mov esp, ebp
378 pop ebp
379 add esp, 8
380 iretd
381
382 CommonInterruptEntry ENDP
383
384 END