1;------------------------------------------------------------------------------ 2; 3; Copyright (c) 2010 - 2015, Intel Corporation. All rights reserved.<BR> 4; 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. 8; 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. 11; 12; Module Name: 13; 14; AsmFuncs.asm 15; 16; Abstract: 17; 18; Debug interrupt handle functions. 19; 20;------------------------------------------------------------------------------ 21 22#include "DebugException.h" 23 24.686p 25.xmm 26.model flat,c 27 28; 29; InterruptProcess() 30; 31InterruptProcess PROTO C 32 33public Exception0Handle, TimerInterruptHandle, ExceptionStubHeaderSize 34 35AGENT_HANDLER_SIGNATURE MACRO 36 db 41h, 47h, 54h, 48h ; SIGNATURE_32('A','G','T','H') 37ENDM 38 39.data 40 41ExceptionStubHeaderSize DD Exception1Handle - Exception0Handle 42CommonEntryAddr DD CommonEntry 43 44.code 45 46AGENT_HANDLER_SIGNATURE 47Exception0Handle: 48 cli 49 push eax 50 mov eax, 0 51 jmp dword ptr [CommonEntryAddr] 52AGENT_HANDLER_SIGNATURE 53Exception1Handle: 54 cli 55 push eax 56 mov eax, 1 57 jmp dword ptr [CommonEntryAddr] 58AGENT_HANDLER_SIGNATURE 59Exception2Handle: 60 cli 61 push eax 62 mov eax, 2 63 jmp dword ptr [CommonEntryAddr] 64AGENT_HANDLER_SIGNATURE 65Exception3Handle: 66 cli 67 push eax 68 mov eax, 3 69 jmp dword ptr [CommonEntryAddr] 70AGENT_HANDLER_SIGNATURE 71Exception4Handle: 72 cli 73 push eax 74 mov eax, 4 75 jmp dword ptr [CommonEntryAddr] 76AGENT_HANDLER_SIGNATURE 77Exception5Handle: 78 cli 79 push eax 80 mov eax, 5 81 jmp dword ptr [CommonEntryAddr] 82AGENT_HANDLER_SIGNATURE 83Exception6Handle: 84 cli 85 push eax 86 mov eax, 6 87 jmp dword ptr [CommonEntryAddr] 88AGENT_HANDLER_SIGNATURE 89Exception7Handle: 90 cli 91 push eax 92 mov eax, 7 93 jmp dword ptr [CommonEntryAddr] 94AGENT_HANDLER_SIGNATURE 95Exception8Handle: 96 cli 97 push eax 98 mov eax, 8 99 jmp dword ptr [CommonEntryAddr] 100AGENT_HANDLER_SIGNATURE 101Exception9Handle: 102 cli 103 push eax 104 mov eax, 9 105 jmp dword ptr [CommonEntryAddr] 106AGENT_HANDLER_SIGNATURE 107Exception10Handle: 108 cli 109 push eax 110 mov eax, 10 111 jmp dword ptr [CommonEntryAddr] 112AGENT_HANDLER_SIGNATURE 113Exception11Handle: 114 cli 115 push eax 116 mov eax, 11 117 jmp dword ptr [CommonEntryAddr] 118AGENT_HANDLER_SIGNATURE 119Exception12Handle: 120 cli 121 push eax 122 mov eax, 12 123 jmp dword ptr [CommonEntryAddr] 124AGENT_HANDLER_SIGNATURE 125Exception13Handle: 126 cli 127 push eax 128 mov eax, 13 129 jmp dword ptr [CommonEntryAddr] 130AGENT_HANDLER_SIGNATURE 131Exception14Handle: 132 cli 133 push eax 134 mov eax, 14 135 jmp dword ptr [CommonEntryAddr] 136AGENT_HANDLER_SIGNATURE 137Exception15Handle: 138 cli 139 push eax 140 mov eax, 15 141 jmp dword ptr [CommonEntryAddr] 142AGENT_HANDLER_SIGNATURE 143Exception16Handle: 144 cli 145 push eax 146 mov eax, 16 147 jmp dword ptr [CommonEntryAddr] 148AGENT_HANDLER_SIGNATURE 149Exception17Handle: 150 cli 151 push eax 152 mov eax, 17 153 jmp dword ptr [CommonEntryAddr] 154AGENT_HANDLER_SIGNATURE 155Exception18Handle: 156 cli 157 push eax 158 mov eax, 18 159 jmp dword ptr [CommonEntryAddr] 160AGENT_HANDLER_SIGNATURE 161Exception19Handle: 162 cli 163 push eax 164 mov eax, 19 165 jmp dword ptr [CommonEntryAddr] 166AGENT_HANDLER_SIGNATURE 167TimerInterruptHandle: 168 cli 169 push eax 170 mov eax, 32 171 jmp dword ptr [CommonEntryAddr] 172 173CommonEntry: 174; 175; +---------------------+ 176; + EFlags + 177; +---------------------+ 178; + CS + 179; +---------------------+ 180; + EIP + 181; +---------------------+ 182; + Error Code + 183; +---------------------+ 184; + EAX / Vector Number + 185; +---------------------+ 186; + EBP + 187; +---------------------+ <-- EBP 188; 189 cmp eax, DEBUG_EXCEPT_DOUBLE_FAULT 190 je NoExtrPush 191 cmp eax, DEBUG_EXCEPT_INVALID_TSS 192 je NoExtrPush 193 cmp eax, DEBUG_EXCEPT_SEG_NOT_PRESENT 194 je NoExtrPush 195 cmp eax, DEBUG_EXCEPT_STACK_FAULT 196 je NoExtrPush 197 cmp eax, DEBUG_EXCEPT_GP_FAULT 198 je NoExtrPush 199 cmp eax, DEBUG_EXCEPT_PAGE_FAULT 200 je NoExtrPush 201 cmp eax, DEBUG_EXCEPT_ALIGNMENT_CHECK 202 je NoExtrPush 203 204 push [esp] 205 mov dword ptr [esp + 4], 0 206 207NoExtrPush: 208 209 push ebp 210 mov ebp, esp ; save esp in ebp 211 ; 212 ; Make stack 16-byte alignment to make sure save fxrstor later 213 ; 214 and esp, 0fffffff0h 215 sub esp, 12 216 217 ; store UINT32 Edi, Esi, Ebp, Ebx, Edx, Ecx, Eax; 218 push dword ptr [ebp + 4] ; original eax 219 push ebx 220 push ecx 221 push edx 222 mov ebx, eax ; save vector in ebx 223 mov eax, ebp 224 add eax, 4 * 6 225 push eax ; original ESP 226 push dword ptr [ebp] ; EBP 227 push esi 228 push edi 229 230 ;; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4; 231 ;; insure FXSAVE/FXRSTOR is enabled in CR4... 232 ;; ... while we're at it, make sure DE is also enabled... 233 mov eax, 1 234 push ebx ; temporarily save value of ebx on stack 235 cpuid ; use CPUID to determine if FXSAVE/FXRESTOR and 236 ; DE are supported 237 pop ebx ; retore value of ebx that was overwritten by CPUID 238 mov eax, cr4 239 push eax ; push cr4 firstly 240 test edx, BIT24 ; Test for FXSAVE/FXRESTOR support 241 jz @F 242 or eax, BIT9 ; Set CR4.OSFXSR 243@@: 244 test edx, BIT2 ; Test for Debugging Extensions support 245 jz @F 246 or eax, BIT3 ; Set CR4.DE 247@@: 248 mov cr4, eax 249 mov eax, cr3 250 push eax 251 mov eax, cr2 252 push eax 253 push 0 ; cr0 will not saved??? 254 mov eax, cr0 255 push eax 256 257 xor ecx, ecx 258 mov ecx, Ss 259 push ecx 260 mov ecx, Cs 261 push ecx 262 mov ecx, Ds 263 push ecx 264 mov ecx, Es 265 push ecx 266 mov ecx, Fs 267 push ecx 268 mov ecx, Gs 269 push ecx 270 271 ;; EIP 272 mov ecx, [ebp + 4 * 3] ; EIP 273 push ecx 274 275 ;; UINT32 Gdtr[2], Idtr[2]; 276 sub esp, 8 277 sidt fword ptr [esp] 278 sub esp, 8 279 sgdt fword ptr [esp] 280 281 ;; UINT32 Ldtr, Tr; 282 xor eax, eax 283 str ax 284 push eax 285 sldt ax 286 push eax 287 288 ;; EFlags 289 mov ecx, [ebp + 4 * 5] 290 push ecx 291 292 ;; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7; 293 mov eax, dr7 294 push eax 295 296 ;; clear Dr7 while executing debugger itself 297 xor eax, eax 298 mov dr7, eax 299 300 ;; Dr6 301 mov eax, dr6 302 push eax 303 304 ;; insure all status bits in dr6 are clear... 305 xor eax, eax 306 mov dr6, eax 307 308 mov eax, dr3 309 push eax 310 mov eax, dr2 311 push eax 312 mov eax, dr1 313 push eax 314 mov eax, dr0 315 push eax 316 317 ;; Clear Direction Flag 318 cld 319 320 ;; FX_SAVE_STATE_IA32 FxSaveState; 321 sub esp, 512 322 mov edi, esp 323 ;; Clear the buffer 324 xor eax, eax 325 mov ecx, 128 ;= 512 / 4 326 rep stosd 327 mov edi, esp 328 329 test edx, BIT24 ; Test for FXSAVE/FXRESTOR support. 330 ; edx still contains result from CPUID above 331 jz @F 332 db 0fh, 0aeh, 00000111y ;fxsave [edi] 333@@: 334 335 ;; save the exception data 336 push dword ptr [ebp + 8] 337 338 ; call the C interrupt process function 339 push esp ; Structure 340 push ebx ; vector 341 call InterruptProcess 342 add esp, 8 343 344 ; skip the exception data 345 add esp, 4 346 347 ;; FX_SAVE_STATE_IA32 FxSaveState; 348 mov esi, esp 349 mov eax, 1 350 cpuid ; use CPUID to determine if FXSAVE/FXRESTOR are supported 351 test edx, BIT24 ; Test for FXSAVE/FXRESTOR support 352 jz @F 353 db 0fh, 0aeh, 00001110y ; fxrstor [esi] 354@@: 355 add esp, 512 356 357 ;; UINT32 Dr0, Dr1, Dr2, Dr3, Dr6, Dr7; 358 pop eax 359 mov dr0, eax 360 pop eax 361 mov dr1, eax 362 pop eax 363 mov dr2, eax 364 pop eax 365 mov dr3, eax 366 ;; skip restore of dr6. We cleared dr6 during the context save. 367 add esp, 4 368 pop eax 369 mov dr7, eax 370 371 ;; set EFlags 372 pop dword ptr [ebp + 4 * 5] ; set EFLAGS in stack 373 374 ;; UINT32 Ldtr, Tr; 375 ;; UINT32 Gdtr[2], Idtr[2]; 376 ;; Best not let anyone mess with these particular registers... 377 add esp, 24 378 379 ;; UINT32 Eip; 380 pop dword ptr [ebp + 4 * 3] ; set EIP in stack 381 382 ;; UINT32 Gs, Fs, Es, Ds, Cs, Ss; 383 ;; NOTE - modified segment registers could hang the debugger... We 384 ;; could attempt to insulate ourselves against this possibility, 385 ;; but that poses risks as well. 386 ;; 387 pop gs 388 pop fs 389 pop es 390 pop ds 391 pop dword ptr [ebp + 4 * 4] ; set CS in stack 392 pop ss 393 394 ;; UINT32 Cr0, Cr1, Cr2, Cr3, Cr4; 395 pop eax 396 mov cr0, eax 397 add esp, 4 ; skip for Cr1 398 pop eax 399 mov cr2, eax 400 pop eax 401 mov cr3, eax 402 pop eax 403 mov cr4, eax 404 405 ;; restore general register 406 pop edi 407 pop esi 408 pop dword ptr [ebp] ; save updated ebp 409 pop dword ptr [ebp + 4] ; save updated esp 410 pop edx 411 pop ecx 412 pop ebx 413 pop eax 414 415 mov esp, ebp 416 pop ebp ; restore ebp maybe updated 417 pop esp ; restore esp maybe updated 418 sub esp, 4 * 3 ; restore interupt pushced stack 419 420 iretd 421 422END 423