Patch that fixes VMWare boot (and should fix QEMu/KVM boot on the testbot):

[NTOS]: A trap can get us into a state where DS/ES are invalid, making any pointer dereference (on DS/ES segmented memory, not SS, the stack) crash (and probably double-fault). Therefore, we have to be careful to switch to a good DS/ES before touching the TrapFrame pointer, which we don't have in ESP like the ASM code, but in a DS/ES-segmented register. For V8086 traps we can switch to the good DS/ES immediately, but for other kinds of traps, we actually need to save the current (bad) segments first. So we save them on the stack now, then switch to the good ones, then store the stack values into the trap frame. This is what happens on a non-optimized (-O0) build. On an optimized build, the segments will end up in registers instead, which is fine too (they'll be direct values). The order of instructions is guaranteed since the segment macros are volatile.
[NTOS]: The GPF and Invalid Opcode handlers are performance critical when talking about V8086 traps, because they control the main flow of execution during that mode (GPFs will be issued for any privileged instruction we need to emulate, and invalid opcode might be generated for BOPs). Because of this, we employ a fast entry/exit macro into V8086 mode since we can make certain assumptions. We detect, and use, such scenarios when the V8086 flag is enabled in EFLAGS. However, because we can land in a GPF handler with an invalid DS/ES, as some V8086 code could trample this during BIOS calls for example, we must make sure that we are on a valid DS/ES before dereferencing any pointer. We fixup DS/ES either in KiEnterTrap (for normal entry/exit) or, for V86, in KiEnterV86Trap. Notice the problem: we need to detect which of these to use early on but we can't touch the EFLAGS in the frame because DS/ES could be invalid. Thankfully SS is always guaranteed valid, so stack dereferences are game! We therefore read the EFLAGS here, in assembly, where we can touch ESP as we please. We save this in EDX, which will be used as the second argument for the FASTCALL C trap entry. When we make the fast V86 check, we use the parameter instead of the trap frame, leading us to using the correct trap entry function, which fixes up DS/ES and lets us go on our merry way...
[NTOS]: Make appropriate changes to GENERATE_TRAP_HANDLERS macro.
[NTOS]: Switch to using well-known NT trap handler names (hex-based, double-zeroed) instead of decimal-based trap handler names which are confusing.
[NTOS]: Clean up some debug spew.

svn path=/trunk/; revision=45052
This commit is contained in:
Sir Richard 2010-01-12 05:50:45 +00:00
parent 66c33fe237
commit 68ca27a00d
6 changed files with 144 additions and 191 deletions

View file

@ -229,16 +229,61 @@ _KiUnexpectedInterrupt&Number:
//
// @remark None.
//
.macro GENERATE_TRAP_HANDLER Name, ErrorCode
.macro GENERATE_TRAP_HANDLER Name, ErrorCode=1, FastV86=0
.func Name
_&Name:
/* Some traps generate an error code, some don't (thanks, Intel!) */
.if \ErrorCode
push 0
.endif
/* Save all register state before we touch it */
pushad
/*
* The GPF and Invalid Opcode handlers are performance critical when talking
* about V8086 traps, because they control the main flow of execution during
* that mode (GPFs will be issued for any privileged instruction we need to
* emulate, and invalid opcode might be generated for BOPs).
*
* Because of this, we employ a fast entry/exit macro into V8086 mode since
* we can make certain assumptions. We detect, and use, such scenarios when
* the V8086 flag is enabled in EFLAGS.
*
* However, because we can land in a GPF handler with an invalid DS/ES, as
* some V8086 code could trample this during BIOS calls for example, we must
* make sure that we are on a valid DS/ES before dereferencing any pointer.
*
* We fixup DS/ES either in KiEnterTrap (for normal entry/exit) or, for V86,
* in KiEnterV86Trap. Notice the problem: we need to detect which of these
* to use early on but we can't touch the EFLAGS in the frame because DS/ES
* could be invalid.
*
* Thankfully SS is always guaranteed valid, so stack dereferences are game!
*
* We therefore read the EFLAGS here, in assembly, where we can touch ESP as
* we please. We save this in EDX, which will be used as the second argument
* for the FASTCALL C trap entry.
*
* When we make the fast V86 check, we use the parameter instead of the trap
* frame, leading us to using the correct trap entry function, which fixes
* up DS/ES and lets us go on our merry way...
*/
.if \FastV86
/* ESP+12 is EFLAGS on interrupt frame, add 8*4 for the PUSHAD frame */
mov edx, [esp+12+8*4]
.endif
/* Now make space for the trap frame and store the pointer as first arg */
sub esp, KTRAP_FRAME_LENGTH - KTRAP_FRAME_PREVIOUS_MODE
mov ecx, esp
jmp @&Name&Handler@4
/* Normally we just have one parameter, but fast V86 handlers need two */
.if \FastV86
jmp @&Name&Handler@8
.else
jmp @&Name&Handler@4
.endif
.endfunc
.endm

View file

@ -440,9 +440,9 @@ extern ULONG KeI386CpuType;
extern ULONG KeI386CpuStep;
extern UCHAR KiDebugRegisterTrapOffsets[9];
extern UCHAR KiDebugRegisterContextOffsets[9];
extern VOID __cdecl KiTrap2(VOID);
extern VOID __cdecl KiTrap8(VOID);
extern VOID __cdecl KiTrap19(VOID);
extern VOID __cdecl KiTrap02(VOID);
extern VOID __cdecl KiTrap08(VOID);
extern VOID __cdecl KiTrap13(VOID);
extern VOID __cdecl KiFastCallEntry(VOID);
extern VOID NTAPI ExpInterlockedPopEntrySListFault(VOID);
extern VOID __cdecl CopyParams(VOID);

View file

@ -651,7 +651,7 @@ Ki386InitializeTss(IN PKTSS Tss,
Tss->CR3 = __readcr3();
Tss->Esp0 = PtrToUlong(KiDoubleFaultStack);
Tss->Esp = PtrToUlong(KiDoubleFaultStack);
Tss->Eip = PtrToUlong(KiTrap8);
Tss->Eip = PtrToUlong(KiTrap08);
Tss->Cs = KGDT_R0_CODE;
Tss->Fs = KGDT_R0_PCR;
Tss->Ss = Ke386GetSs();
@ -681,7 +681,7 @@ Ki386InitializeTss(IN PKTSS Tss,
Tss->CR3 = __readcr3();
Tss->Esp0 = PtrToUlong(KiDoubleFaultStack);
Tss->Esp = PtrToUlong(KiDoubleFaultStack);
Tss->Eip = PtrToUlong(KiTrap2);
Tss->Eip = PtrToUlong(KiTrap02);
Tss->Cs = KGDT_R0_CODE;
Tss->Fs = KGDT_R0_PCR;
Tss->Ss = Ke386GetSs();
@ -837,13 +837,13 @@ Ki386EnableXMMIExceptions(IN ULONG_PTR Context)
{
PKIDTENTRY IdtEntry;
/* Get the IDT Entry for Interrupt 19 */
IdtEntry = &((PKIPCR)KeGetPcr())->IDT[19];
/* Get the IDT Entry for Interrupt 0x13 */
IdtEntry = &((PKIPCR)KeGetPcr())->IDT[0x13];
/* Set it up */
IdtEntry->Selector = KGDT_R0_CODE;
IdtEntry->Offset = ((ULONG_PTR)KiTrap19 & 0xFFFF);
IdtEntry->ExtendedOffset = ((ULONG_PTR)KiTrap19 >> 16) & 0xFFFF;
IdtEntry->Offset = ((ULONG_PTR)KiTrap13 & 0xFFFF);
IdtEntry->ExtendedOffset = ((ULONG_PTR)KiTrap13 >> 16) & 0xFFFF;
((PKIDT_ACCESS)&IdtEntry->Access)->Dpl = 0;
((PKIDT_ACCESS)&IdtEntry->Access)->Present = 1;
((PKIDT_ACCESS)&IdtEntry->Access)->SegmentType = I386_INTERRUPT_GATE;

View file

@ -22,24 +22,24 @@
.globl _KiIdt
_KiIdt:
/* This is the Software Interrupt Table that we handle in this file: */
idt _KiTrap0, INT_32_DPL0 /* INT 00: Divide Error (#DE) */
idt _KiTrap1, INT_32_DPL0 /* INT 01: Debug Exception (#DB) */
idt _KiTrap2, INT_32_DPL0 /* INT 02: NMI Interrupt */
idt _KiTrap3, INT_32_DPL3 /* INT 03: Breakpoint Exception (#BP) */
idt _KiTrap4, INT_32_DPL3 /* INT 04: Overflow Exception (#OF) */
idt _KiTrap5, INT_32_DPL0 /* INT 05: BOUND Range Exceeded (#BR) */
idt _KiTrap6, INT_32_DPL0 /* INT 06: Invalid Opcode Code (#UD) */
idt _KiTrap7, INT_32_DPL0 /* INT 07: Device Not Available (#NM) */
idt _KiTrap8, INT_32_DPL0 /* INT 08: Double Fault Exception (#DF) */
idt _KiTrap9, INT_32_DPL0 /* INT 09: RESERVED */
idt _KiTrap10, INT_32_DPL0 /* INT 0A: Invalid TSS Exception (#TS) */
idt _KiTrap11, INT_32_DPL0 /* INT 0B: Segment Not Present (#NP) */
idt _KiTrap12, INT_32_DPL0 /* INT 0C: Stack Fault Exception (#SS) */
idt _KiTrap13, INT_32_DPL0 /* INT 0D: General Protection (#GP) */
idt _KiTrap14, INT_32_DPL0 /* INT 0E: Page-Fault Exception (#PF) */
idt _KiTrap00, INT_32_DPL0 /* INT 00: Divide Error (#DE) */
idt _KiTrap01, INT_32_DPL0 /* INT 01: Debug Exception (#DB) */
idt _KiTrap02, INT_32_DPL0 /* INT 02: NMI Interrupt */
idt _KiTrap03, INT_32_DPL3 /* INT 03: Breakpoint Exception (#BP) */
idt _KiTrap04, INT_32_DPL3 /* INT 04: Overflow Exception (#OF) */
idt _KiTrap05, INT_32_DPL0 /* INT 05: BOUND Range Exceeded (#BR) */
idt _KiTrap06, INT_32_DPL0 /* INT 06: Invalid Opcode Code (#UD) */
idt _KiTrap07, INT_32_DPL0 /* INT 07: Device Not Available (#NM) */
idt _KiTrap08, INT_32_DPL0 /* INT 08: Double Fault Exception (#DF) */
idt _KiTrap09, INT_32_DPL0 /* INT 09: RESERVED */
idt _KiTrap0A, INT_32_DPL0 /* INT 0A: Invalid TSS Exception (#TS) */
idt _KiTrap0B, INT_32_DPL0 /* INT 0B: Segment Not Present (#NP) */
idt _KiTrap0C, INT_32_DPL0 /* INT 0C: Stack Fault Exception (#SS) */
idt _KiTrap0D, INT_32_DPL0 /* INT 0D: General Protection (#GP) */
idt _KiTrap0E, INT_32_DPL0 /* INT 0E: Page-Fault Exception (#PF) */
idt _KiTrap0F, INT_32_DPL0 /* INT 0F: RESERVED */
idt _KiTrap16, INT_32_DPL0 /* INT 10: x87 FPU Error (#MF) */
idt _KiTrap17, INT_32_DPL0 /* INT 11: Align Check Exception (#AC) */
idt _KiTrap10, INT_32_DPL0 /* INT 10: x87 FPU Error (#MF) */
idt _KiTrap11, INT_32_DPL0 /* INT 11: Align Check Exception (#AC) */
idt _KiTrap0F, INT_32_DPL0 /* INT 12: Machine Check Exception (#MC)*/
idt _KiTrap0F, INT_32_DPL0 /* INT 13: SIMD FPU Exception (#XF) */
.rept 22
@ -54,8 +54,8 @@ idt _KiTrap0F, INT_32_DPL0 /* INT 2F: RESERVED */
GENERATE_IDT_STUBS /* INT 30-FF: UNEXPECTED INTERRUPTS */
/* Trap handlers referenced from C code */
.globl _KiTrap8
.globl _KiTrap19
.globl _KiTrap08
.globl _KiTrap13
/* System call code referenced from C code */
.globl _CopyParams
@ -383,7 +383,7 @@ BadStack:
push 0x20202
push KGDT_R3_CODE + RPL_MASK
push 0
jmp _KiTrap6
jmp _KiTrap06
#if DBG
InvalidIrql:
@ -573,127 +573,24 @@ Error:
/* HARDWARE TRAP HANDLERS ****************************************************/
GENERATE_TRAP_HANDLER KiTrap0, 1
GENERATE_TRAP_HANDLER KiTrap1, 1
GENERATE_TRAP_HANDLER KiTrap3, 1
GENERATE_TRAP_HANDLER KiTrap4, 1
GENERATE_TRAP_HANDLER KiTrap5, 1
GENERATE_TRAP_HANDLER KiTrap6, 1
GENERATE_TRAP_HANDLER KiTrap7, 1
GENERATE_TRAP_HANDLER KiTrap8, 0
GENERATE_TRAP_HANDLER KiTrap9, 1
GENERATE_TRAP_HANDLER KiTrap10, 0
GENERATE_TRAP_HANDLER KiTrap11, 0
GENERATE_TRAP_HANDLER KiTrap12, 0
//GENERATE_TRAP_HANDLER KiTrap13, 0
.func KiTrap13
TRAP_FIXUPS kitd_a, kitd_t, DoFixupV86, DoNotFixupAbios
_KiTrap13:
/* It this a V86 GPF? */
test dword ptr [esp+12], EFLAGS_V86_MASK
jz NotV86
/* Enter V86 Trap */
V86_TRAP_PROLOG kitd_a, kitd_v
/* Make sure that this is a V86 process */
mov ecx, PCR[KPCR_CURRENT_THREAD]
mov ecx, [ecx+KTHREAD_APCSTATE_PROCESS]
cmp dword ptr [ecx+EPROCESS_VDM_OBJECTS], 0
jz ShouldNotGetHere
RaiseIrql:
/* Go to APC level */
mov ecx, APC_LEVEL
call @KfRaiseIrql@4
/* Save old IRQL and enable interrupts */
push eax
sti
/* Handle the opcode */
mov ecx, ebp
call @Ki386HandleOpcodeV86@4
/* Check if this was VDM */
test al, 0xFF
jz ShouldNotGetHere
NoReflect:
/* Lower IRQL and disable interrupts */
pop ecx
call @KfLowerIrql@4
cli
/* Check if this was a V86 trap */
test dword ptr [ebp+KTRAP_FRAME_EFLAGS], EFLAGS_V86_MASK
jz NotV86Trap
/* Exit the V86 Trap */
V86_TRAP_EPILOG
NotV86Trap:
/* Either this wasn't V86, or it was, but an APC interrupted us */
jmp _Kei386EoiHelper@0
NotV86:
/* Enter trap */
TRAP_PROLOG kitd_a, kitd_t
/* Check if this was from kernel-mode */
test dword ptr [ebp+KTRAP_FRAME_CS], MODE_MASK
jnz ShouldNotGetHere
/* Get the opcode and trap frame */
KmodeGpf:
mov eax, [ebp+KTRAP_FRAME_EIP]
mov eax, [eax]
mov edx, [ebp+KTRAP_FRAME_EBP]
/* Was it IRETD? */
cmp al, 0xCF
jne ShouldNotGetHere
/* Get error code */
lea edx, [ebp+KTRAP_FRAME_ESP]
mov ax, [ebp+KTRAP_FRAME_ERROR_CODE]
and ax, ~RPL_MASK
/* Get CS */
mov cx, word ptr [edx+4]
and cx, ~RPL_MASK
cmp cx, ax
jnz ShouldNotGetHere
/* This should be a Ki386CallBios return */
mov eax, offset @Ki386BiosCallReturnAddress@4
cmp eax, [edx]
jne ShouldNotGetHere
mov eax, [edx+4]
cmp ax, KGDT_R0_CODE + RPL_MASK
jne ShouldNotGetHere
/* Jump to return address */
mov ecx, ebp
jmp @Ki386BiosCallReturnAddress@4
_Ki16BitStackException:
ShouldNotGetHere:
/* FIXME */
UNHANDLED_PATH "Other GPF stuff"
.endfunc
GENERATE_TRAP_HANDLER KiTrap14, 0
GENERATE_TRAP_HANDLER KiTrap0F, 1
GENERATE_TRAP_HANDLER KiTrap16, 1
GENERATE_TRAP_HANDLER KiTrap17, 1
GENERATE_TRAP_HANDLER KiTrap19, 1
GENERATE_TRAP_HANDLER KiTrap00
GENERATE_TRAP_HANDLER KiTrap01
GENERATE_TRAP_HANDLER KiTrap03
GENERATE_TRAP_HANDLER KiTrap04
GENERATE_TRAP_HANDLER KiTrap05
GENERATE_TRAP_HANDLER KiTrap06
GENERATE_TRAP_HANDLER KiTrap07
GENERATE_TRAP_HANDLER KiTrap08, 0
GENERATE_TRAP_HANDLER KiTrap09
GENERATE_TRAP_HANDLER KiTrap0A, 0
GENERATE_TRAP_HANDLER KiTrap0B, 0
GENERATE_TRAP_HANDLER KiTrap0C, 0
GENERATE_TRAP_HANDLER KiTrap0D, 0, 1
GENERATE_TRAP_HANDLER KiTrap0E, 0
GENERATE_TRAP_HANDLER KiTrap0F
GENERATE_TRAP_HANDLER KiTrap10
GENERATE_TRAP_HANDLER KiTrap11
GENERATE_TRAP_HANDLER KiTrap13
/* UNEXPECTED INTERRUPT HANDLERS **********************************************/

View file

@ -203,14 +203,14 @@ VOID
FASTCALL
KiEnterV86Trap(IN PKTRAP_FRAME TrapFrame)
{
/* Save registers */
KiTrapFrameFromPushaStack(TrapFrame);
/* Load correct registers */
Ke386SetFs(KGDT_R0_PCR);
Ke386SetDs(KGDT_R3_DATA | RPL_MASK);
Ke386SetEs(KGDT_R3_DATA | RPL_MASK);
/* Save registers */
KiTrapFrameFromPushaStack(TrapFrame);
/* Save exception list and bogus previous mode */
TrapFrame->PreviousPreviousMode = -1;
TrapFrame->ExceptionList = KeGetPcr()->Tib.ExceptionList;
@ -283,17 +283,32 @@ VOID
FASTCALL
KiEnterTrap(IN PKTRAP_FRAME TrapFrame)
{
/* Save registers */
KiTrapFrameFromPushaStack(TrapFrame);
ULONG Ds, Es;
/* Save segments and then switch to correct ones */
TrapFrame->SegFs = Ke386GetFs();
TrapFrame->SegGs = Ke386GetGs();
TrapFrame->SegDs = Ke386GetDs();
TrapFrame->SegEs = Ke386GetEs();
Ke386SetFs(KGDT_R0_PCR);
/*
* We really have to get a good DS/ES first before touching any data.
*
* These two reads will either go in a register (with optimizations ON) or
* a stack variable (which is on SS:ESP, guaranteed to be good/valid).
*
* Because the assembly is marked volatile, the order of instructions is
* as-is, otherwise the optimizer could simply get rid of our DS/ES.
*
*/
Ds = Ke386GetDs();
Es = Ke386GetEs();
Ke386SetDs(KGDT_R3_DATA | RPL_MASK);
Ke386SetEs(KGDT_R3_DATA | RPL_MASK);
TrapFrame->SegDs = Ds;
TrapFrame->SegEs = Es;
/* Now we can save the other segments and then switch to the correct FS */
TrapFrame->SegFs = Ke386GetFs();
TrapFrame->SegGs = Ke386GetGs();
Ke386SetFs(KGDT_R0_PCR);
/* Save registers */
KiTrapFrameFromPushaStack(TrapFrame);
/* Save exception list and bogus previous mode */
TrapFrame->PreviousPreviousMode = -1;
@ -568,7 +583,7 @@ KiNpxHandler(IN PKTRAP_FRAME TrapFrame,
VOID
FASTCALL
KiTrap0Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap00Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -587,7 +602,7 @@ KiTrap0Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap1Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap01Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -606,7 +621,7 @@ KiTrap1Handler(IN PKTRAP_FRAME TrapFrame)
}
VOID
KiTrap2(VOID)
KiTrap02(VOID)
{
PKTSS Tss, NmiTss;
PKTHREAD Thread;
@ -752,7 +767,7 @@ KiTrap2(VOID)
VOID
FASTCALL
KiTrap3Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap03Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -763,7 +778,7 @@ KiTrap3Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap4Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap04Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -782,7 +797,7 @@ KiTrap4Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap5Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap05Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -804,7 +819,7 @@ KiTrap5Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap6Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap06Handler(IN PKTRAP_FRAME TrapFrame)
{
PUCHAR Instruction;
ULONG i;
@ -849,7 +864,7 @@ KiTrap6Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap7Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap07Handler(IN PKTRAP_FRAME TrapFrame)
{
PKTHREAD Thread, NpxThread;
PFX_SAVE_AREA SaveArea, NpxSaveArea;
@ -958,7 +973,7 @@ KiTrap7Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap8Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap08Handler(IN PKTRAP_FRAME TrapFrame)
{
/* FIXME: Not handled */
KiSystemFatalException(EXCEPTION_DOUBLE_FAULT, TrapFrame);
@ -966,7 +981,7 @@ KiTrap8Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap9Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap09Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -978,7 +993,7 @@ KiTrap9Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap10Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap0AHandler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -992,7 +1007,7 @@ KiTrap10Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap11Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap0BHandler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -1004,7 +1019,7 @@ KiTrap11Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap12Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap0CHandler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -1016,7 +1031,8 @@ KiTrap12Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap13Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap0DHandler(IN PKTRAP_FRAME TrapFrame,
IN ULONG EFlags)
{
ULONG i, j, Iopl;
BOOLEAN Privileged = FALSE;
@ -1025,7 +1041,7 @@ KiTrap13Handler(IN PKTRAP_FRAME TrapFrame)
KIRQL OldIrql;
/* Check for V86 GPF */
if (TrapFrame->EFlags & EFLAGS_V86_MASK)
if (EFlags & EFLAGS_V86_MASK)
{
/* Enter V86 trap */
KiEnterV86Trap(TrapFrame);
@ -1064,16 +1080,13 @@ KiTrap13Handler(IN PKTRAP_FRAME TrapFrame)
/* Exit trap the slow way */
KiEoiHelper(TrapFrame);
}
/* Save trap frame */
KiEnterTrap(TrapFrame);
/* Check for user-mode GPF */
if (KiUserTrap(TrapFrame))
{
/* Must be user-mode! */
if (!KiUserTrap(TrapFrame)) KiSystemFatalException(EXCEPTION_GP_FAULT, TrapFrame);
{
/* Should not be VDM */
ASSERT(KiVdmTrap(TrapFrame) == FALSE);
@ -1204,8 +1217,8 @@ KiTrap13Handler(IN PKTRAP_FRAME TrapFrame)
* with an invalid CS, which will generate another GPF instead.
*
*/
if (((PVOID)TrapFrame->Eip >= (PVOID)KiTrap13Handler) &&
((PVOID)TrapFrame->Eip < (PVOID)KiTrap13Handler))
if (((PVOID)TrapFrame->Eip >= (PVOID)KiTrap0DHandler) &&
((PVOID)TrapFrame->Eip < (PVOID)KiTrap0DHandler))
{
/* Not implemented */
UNIMPLEMENTED;
@ -1298,7 +1311,7 @@ KiTrap13Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap14Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap0EHandler(IN PKTRAP_FRAME TrapFrame)
{
PKTHREAD Thread;
ULONG_PTR Cr2;
@ -1432,7 +1445,7 @@ KiTrap0FHandler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap16Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap10Handler(IN PKTRAP_FRAME TrapFrame)
{
PKTHREAD Thread;
PFX_SAVE_AREA SaveArea;
@ -1459,7 +1472,7 @@ KiTrap16Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap17Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap11Handler(IN PKTRAP_FRAME TrapFrame)
{
/* Save trap frame */
KiEnterTrap(TrapFrame);
@ -1471,7 +1484,7 @@ KiTrap17Handler(IN PKTRAP_FRAME TrapFrame)
VOID
FASTCALL
KiTrap19Handler(IN PKTRAP_FRAME TrapFrame)
KiTrap13Handler(IN PKTRAP_FRAME TrapFrame)
{
PKTHREAD Thread;
PFX_SAVE_AREA SaveArea;

View file

@ -623,9 +623,7 @@ Ke386CallBios(IN ULONG Int,
Tss->IoMapBase = (USHORT)IOPM_OFFSET;
/* Switch stacks and work the magic */
DPRINT1("Entering V86 mode\n");
Ki386SetupAndExitToV86Mode(VdmTeb);
DPRINT1("Left V86 mode\n");
/* Restore IOPM */
RtlCopyMemory(&Tss->IoMaps[0].IoMap, Ki386IopmSaveArea, PAGE_SIZE * 2);