diff --git a/reactos/ntoskrnl/deprecated/irq.c b/reactos/ntoskrnl/deprecated/irq.c index 68cce62769c..e96fc70eae7 100644 --- a/reactos/ntoskrnl/deprecated/irq.c +++ b/reactos/ntoskrnl/deprecated/irq.c @@ -142,7 +142,6 @@ static ISR_TABLE IsrTable[NR_IRQS][1]; #endif #define TAG_ISR_LOCK TAG('I', 'S', 'R', 'L') -extern IDT_DESCRIPTOR KiIdt[256]; /* FUNCTIONS ****************************************************************/ @@ -162,8 +161,8 @@ KeInitInterrupts (VOID) */ for (i=0;ia=(irq_handler[i]&0xffff)+(KGDT_R0_CODE<<16); + ((IDT_DESCRIPTOR*)&KiIdt[IRQ_BASE+i])->b=(irq_handler[i]&0xffff0000)+PRESENT+ I486_INTERRUPT_GATE; #ifdef CONFIG_SMP for (j = 0; j < MAXIMUM_PROCESSORS; j++) diff --git a/reactos/ntoskrnl/include/internal/ke.h b/reactos/ntoskrnl/include/internal/ke.h index c4ce57f6a14..20f4e47ce4a 100644 --- a/reactos/ntoskrnl/include/internal/ke.h +++ b/reactos/ntoskrnl/include/internal/ke.h @@ -75,6 +75,7 @@ extern PVOID Ki386IopmSaveArea; extern ULONG KeI386EFlagsAndMaskV86; extern ULONG KeI386EFlagsOrMaskV86; extern BOOLEAN KeI386VirtualIntExtensions; +extern KIDTENTRY KiIdt[]; /* MACROS *************************************************************************/ @@ -145,6 +146,8 @@ extern KSPIN_LOCK DispatcherDatabaseLock; #define IOPM_OFFSET FIELD_OFFSET(KTSS, IoMaps[0].IoMap) +#define SIZE_OF_FX_REGISTERS 32 + /* INTERNAL KERNEL FUNCTIONS ************************************************/ /* threadsch.c ********************************************************************/ @@ -677,14 +680,6 @@ KeBugCheckWithTf( PKTRAP_FRAME Tf ); -VOID -STDCALL -KiDumpTrapFrame( - PKTRAP_FRAME Tf, - ULONG ExceptionNr, - ULONG cr2 -); - VOID STDCALL KeFlushCurrentTb(VOID); @@ -757,6 +752,12 @@ KeI386VdmInitialize( VOID ); +VOID +NTAPI +KiFlushNPXState( + IN FLOATING_SAVE_AREA *SaveArea +); + #include "ke_x.h" #endif /* __NTOSKRNL_INCLUDE_INTERNAL_KE_H */ diff --git a/reactos/ntoskrnl/kd/kdinit.c b/reactos/ntoskrnl/kd/kdinit.c index cb72a1c9192..91112cf7064 100644 --- a/reactos/ntoskrnl/kd/kdinit.c +++ b/reactos/ntoskrnl/kd/kdinit.c @@ -74,6 +74,7 @@ KdpGetWrapperDebugMode(PCHAR Currentp2, #ifdef KDBG /* Get the KDBG Settings and enable it */ KdDebuggerEnabled = TRUE; + KdDebuggerNotPresent = FALSE; KdpDebugMode.Gdb = TRUE; KdbpGetCommandLineSettings((PCHAR)LoaderBlock->CommandLine); #endif @@ -183,6 +184,7 @@ KdInitSystem(ULONG BootPhase, p2 += 10; p2 = KdpGetDebugMode(p2); p2 = KdpGetWrapperDebugMode(p2, LoaderBlock); + KdDebuggerEnabled = TRUE; } /* Check for early breakpoint */ else if (!_strnicmp(p2, "BREAK", 5)) diff --git a/reactos/ntoskrnl/kd/kdmain.c b/reactos/ntoskrnl/kd/kdmain.c index 88b5e0424f1..1a55f5ee26c 100644 --- a/reactos/ntoskrnl/kd/kdmain.c +++ b/reactos/ntoskrnl/kd/kdmain.c @@ -105,8 +105,8 @@ KdpEnterDebuggerException(PEXCEPTION_RECORD ExceptionRecord, BOOLEAN FirstChance, BOOLEAN Gdb) { - /* Get out of here if the Debugger isn't enabled */ - if (!KdDebuggerEnabled) return kdHandleException; + /* Get out of here if the Debugger isn't connected */ + if (KdDebuggerNotPresent) return kdHandleException; /* FIXME: * Right now, the GDB wrapper seems to handle exceptions differntly diff --git a/reactos/ntoskrnl/ke/bug.c b/reactos/ntoskrnl/ke/bug.c index d471ca40773..4ec0d27ce8b 100644 --- a/reactos/ntoskrnl/ke/bug.c +++ b/reactos/ntoskrnl/ke/bug.c @@ -1,15 +1,12 @@ /* - * COPYRIGHT: See COPYING in the top level directory - * PROJECT: ReactOS kernel + * PROJECT: ReactOS Kernel + * LICENSE: GPL - See COPYING in the top level directory * FILE: ntoskrnl/ke/bug.c - * PURPOSE: Graceful system shutdown if a bug is detected - * - * PROGRAMMERS: Alex Ionescu - Rewrote Bugcheck Routines and implemented Reason Callbacks. - * David Welch (welch@cwcom.net) - * Phillip Susi + * PURPOSE: Bugcheck Support + * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org) */ -/* INCLUDES *****************************************************************/ +/* INCLUDES ******************************************************************/ #include #define NDEBUG @@ -29,15 +26,168 @@ HalReleaseDisplayOwnership( extern FAST_MUTEX KernelAddressSpaceLock; -/* GLOBALS ******************************************************************/ +/* GLOBALS *******************************************************************/ -static LIST_ENTRY BugcheckCallbackListHead = {NULL,NULL}; -static LIST_ENTRY BugcheckReasonCallbackListHead = {NULL,NULL}; -static ULONG InBugCheck; -static PRTL_MESSAGE_RESOURCE_DATA KiBugCodeMessages; -static ULONG KeBugCheckCount = 1; +LIST_ENTRY BugcheckCallbackListHead = {NULL,NULL}; +LIST_ENTRY BugcheckReasonCallbackListHead = {NULL,NULL}; +ULONG KeBugCheckActive, KeBugCheckOwner; +LONG KeBugCheckOwnerRecursionCount; +PRTL_MESSAGE_RESOURCE_DATA KiBugCodeMessages; +ULONG KeBugCheckCount = 1; +ULONG KiHardwareTrigger; +PUNICODE_STRING KiBugCheckDriver; +ULONG_PTR KiBugCheckData[5]; -/* FUNCTIONS *****************************************************************/ +typedef PCHAR +(NTAPI *PKE_BUGCHECK_UNICODE_TO_ANSI)( + IN PUNICODE_STRING Unicode, + IN PCHAR Ansi, + IN ULONG Length +); + +/* PRIVATE FUNCTIONS *********************************************************/ + +BOOLEAN +NTAPI +KiRosPrintAddress(PVOID address) +{ + PLIST_ENTRY current_entry; + PLDR_DATA_TABLE_ENTRY current; + extern LIST_ENTRY ModuleListHead; + ULONG_PTR RelativeAddress; + ULONG i = 0; + + do + { + current_entry = ModuleListHead.Flink; + + while (current_entry != &ModuleListHead) + { + current = CONTAINING_RECORD(current_entry, + LDR_DATA_TABLE_ENTRY, + InLoadOrderLinks); + + if (address >= (PVOID)current->DllBase && + address < (PVOID)((ULONG_PTR)current->DllBase + + current->SizeOfImage)) + { + RelativeAddress = (ULONG_PTR)address - + (ULONG_PTR)current->DllBase; + DbgPrint("<%wZ: %x>", ¤t->FullDllName, RelativeAddress); + return(TRUE); + } + current_entry = current_entry->Flink; + } + } while(++i <= 1); + + return(FALSE); +} + +ULONG +NTAPI +KeRosGetStackFrames(PULONG Frames, + ULONG FrameCount) +{ + ULONG Count = 0; + PULONG StackBase, StackEnd, Frame; + MEMORY_BASIC_INFORMATION mbi; + ULONG ResultLength = sizeof(mbi); + NTSTATUS Status; + + _SEH_TRY + { +#if defined __GNUC__ + __asm__("mov %%ebp, %0" : "=r" (Frame) : ); +#elif defined(_MSC_VER) + __asm mov [Frame], ebp +#endif + + Status = MiQueryVirtualMemory ( + (HANDLE)-1, + Frame, + MemoryBasicInformation, + &mbi, + sizeof(mbi), + &ResultLength ); + if ( !NT_SUCCESS(Status) ) + { + DPRINT1("Can't get stack frames: MiQueryVirtualMemory() failed: %x\n", Status ); + return 0; + } + + StackBase = Frame; + StackEnd = (PULONG)((ULONG_PTR)mbi.BaseAddress + mbi.RegionSize); + + while ( Count < FrameCount && Frame >= StackBase && Frame < StackEnd ) + { + Frames[Count++] = Frame[1]; + StackBase = Frame; + Frame = (PULONG)Frame[0]; + } + } + _SEH_HANDLE + { + } + _SEH_END; + return Count; +} + +VOID +NTAPI +KeDumpStackFrames(PULONG Frame) +{ + /* Just call the extended version */ + KeRosDumpStackFrames(Frame, 0); +} + +VOID +NTAPI +KeRosDumpStackFrames(IN PULONG Frame OPTIONAL, + IN ULONG FrameCount OPTIONAL) +{ + ULONG Frames[32]; + ULONG Count, i, Addr; + + /* Don't let anyone ask more then 32 frames */ + if (FrameCount > 32) return; + + /* If the caller didn't ask, assume 32 frames */ + if (!FrameCount) FrameCount = 32; + + /* Get the current frames, and make sure caller didn't ask too many */ + Count = KeRosGetStackFrames(Frames, FrameCount); // <= should be replaced with Rtl + if (FrameCount > Count) FrameCount = Count; + + /* Now loop them (skip the two. One for the dumper, one for the caller) */ + for (i = 2; i < FrameCount; i++) + { + /* Get the EIP */ + Addr = Frames[i]; + + /* If we had a custom frame, make sure we've reached it first */ + if ((Frame) && (Frame[1] == Addr)) + { + Frame = NULL; + } + else if (Frame) + { + /* Skip this entry */ + continue; + } + + /* Print it out */ + if (!KeRosPrintAddress((PVOID)Addr)) DbgPrint("<%X>", Addr); + + /* Break out of invalid addresses */ + if (Addr == 0 || Addr == 0xDEADBEEF) break; + + /* Go to the next frame */ + DbgPrint("\n"); + } + + /* Finish the output */ + DbgPrint("\n"); +} VOID INIT_FUNCTION @@ -52,7 +202,6 @@ KiInitializeBugCheck(VOID) /* Initialize Callbadk Listhead and State */ InitializeListHead(&BugcheckCallbackListHead); InitializeListHead(&BugcheckReasonCallbackListHead); - InBugCheck = 0; /* Cache the Bugcheck Message Strings. Prepare the Lookup Data */ ResourceInfo.Type = 11; @@ -66,194 +215,63 @@ KiInitializeBugCheck(VOID) &ResourceDataEntry); /* Make sure it worked */ - if (NT_SUCCESS(Status)) { - - DPRINT("Found Bugcheck Resource Data!\n"); - + if (NT_SUCCESS(Status)) + { /* Now actually get a pointer to it */ Status = LdrAccessResource((PVOID)KERNEL_BASE, ResourceDataEntry, (PVOID*)&BugCheckData, NULL); - - /* Make sure it worked */ - if (NT_SUCCESS(Status)) { - - DPRINT("Got Pointer to Bugcheck Resource Data!\n"); - KiBugCodeMessages = BugCheckData; - } + if (NT_SUCCESS(Status)) KiBugCodeMessages = BugCheckData; } } -/* - * @implemented - */ -BOOLEAN -STDCALL -KeDeregisterBugCheckCallback(PKBUGCHECK_CALLBACK_RECORD CallbackRecord) -{ - KIRQL OldIrql; - BOOLEAN Status = FALSE; - - /* Raise IRQL to High */ - KeRaiseIrql(HIGH_LEVEL, &OldIrql); - - /* Check the Current State */ - if (CallbackRecord->State == BufferInserted) { - - /* Reset state and remove from list */ - CallbackRecord->State = BufferEmpty; - RemoveEntryList(&CallbackRecord->Entry); - - Status = TRUE; - } - - /* Lower IRQL and return */ - KeLowerIrql(OldIrql); - return Status; -} - -/* - * @implemented - */ -BOOLEAN -STDCALL -KeDeregisterBugCheckReasonCallback(IN PKBUGCHECK_REASON_CALLBACK_RECORD CallbackRecord) -{ - KIRQL OldIrql; - BOOLEAN Status = FALSE; - - /* Raise IRQL to High */ - KeRaiseIrql(HIGH_LEVEL, &OldIrql); - - /* Check the Current State */ - if (CallbackRecord->State == BufferInserted) { - - /* Reset state and remove from list */ - CallbackRecord->State = BufferEmpty; - RemoveEntryList(&CallbackRecord->Entry); - - Status = TRUE; - } - - /* Lower IRQL and return */ - KeLowerIrql(OldIrql); - return Status; -} - -/* - * @implemented - */ -BOOLEAN -STDCALL -KeRegisterBugCheckCallback(PKBUGCHECK_CALLBACK_RECORD CallbackRecord, - PKBUGCHECK_CALLBACK_ROUTINE CallbackRoutine, - PVOID Buffer, - ULONG Length, - PUCHAR Component) -{ - KIRQL OldIrql; - BOOLEAN Status = FALSE; - - /* Raise IRQL to High */ - KeRaiseIrql(HIGH_LEVEL, &OldIrql); - - /* Check the Current State first so we don't double-register */ - if (CallbackRecord->State == BufferEmpty) { - - /* Set the Callback Settings and insert into the list */ - CallbackRecord->Length = Length; - CallbackRecord->Buffer = Buffer; - CallbackRecord->Component = Component; - CallbackRecord->CallbackRoutine = CallbackRoutine; - CallbackRecord->State = BufferInserted; - InsertTailList(&BugcheckCallbackListHead, &CallbackRecord->Entry); - - Status = TRUE; - } - - /* Lower IRQL and return */ - KeLowerIrql(OldIrql); - return Status; -} - -/* - * @implemented - */ -BOOLEAN -STDCALL -KeRegisterBugCheckReasonCallback(IN PKBUGCHECK_REASON_CALLBACK_RECORD CallbackRecord, - IN PKBUGCHECK_REASON_CALLBACK_ROUTINE CallbackRoutine, - IN KBUGCHECK_CALLBACK_REASON Reason, - IN PUCHAR Component) -{ - KIRQL OldIrql; - BOOLEAN Status = FALSE; - - /* Raise IRQL to High */ - KeRaiseIrql(HIGH_LEVEL, &OldIrql); - - /* Check the Current State first so we don't double-register */ - if (CallbackRecord->State == BufferEmpty) { - - /* Set the Callback Settings and insert into the list */ - CallbackRecord->Component = Component; - CallbackRecord->CallbackRoutine = CallbackRoutine; - CallbackRecord->State = BufferInserted; - CallbackRecord->Reason = Reason; - InsertTailList(&BugcheckReasonCallbackListHead, &CallbackRecord->Entry); - - Status = TRUE; - } - - /* Lower IRQL and return */ - KeLowerIrql(OldIrql); - return Status; -} - VOID -STDCALL -KeGetBugMessageText(ULONG BugCheckCode, PANSI_STRING OutputString) +NTAPI +KeGetBugMessageText(IN ULONG BugCheckCode, + OUT PANSI_STRING OutputString OPTIONAL) { ULONG i; ULONG IdOffset; ULONG_PTR MessageEntry; PCHAR BugCode; - /* Find the message. This code is based on RtlFindMesssage -- Alex */ - for (i = 0; i < KiBugCodeMessages->NumberOfBlocks; i++) + /* Find the message. This code is based on RtlFindMesssage */ + for (i = 0; i < KiBugCodeMessages->NumberOfBlocks; i++) { /* Check if the ID Matches */ if ((BugCheckCode >= KiBugCodeMessages->Blocks[i].LowId) && - (BugCheckCode <= KiBugCodeMessages->Blocks[i].HighId)) + (BugCheckCode <= KiBugCodeMessages->Blocks[i].HighId)) { /* Get Offset to Entry */ - MessageEntry = (ULONG_PTR)KiBugCodeMessages + KiBugCodeMessages->Blocks[i].OffsetToEntries; + MessageEntry = KiBugCodeMessages->Blocks[i].OffsetToEntries + + (ULONG_PTR)KiBugCodeMessages; IdOffset = BugCheckCode - KiBugCodeMessages->Blocks[i].LowId; /* Get offset to ID */ for (i = 0; i < IdOffset; i++) { /* Advance in the Entries */ - MessageEntry += ((PRTL_MESSAGE_RESOURCE_ENTRY)MessageEntry)->Length; + MessageEntry += ((PRTL_MESSAGE_RESOURCE_ENTRY)MessageEntry)-> + Length; } /* Get the final Code */ BugCode = ((PRTL_MESSAGE_RESOURCE_ENTRY)MessageEntry)->Text; + i = strlen(BugCode); /* Return it in the OutputString */ - if (OutputString) + if (OutputString) { OutputString->Buffer = BugCode; - OutputString->Length = strlen(BugCode) + 1; - OutputString->MaximumLength = strlen(BugCode) + 1; + OutputString->Length = i + 1; + OutputString->MaximumLength = i + 1; } else { /* Direct Output to Screen */ - CHAR BugString[100]; - sprintf(BugString, "%s\n", BugCode); - InbvDisplayString(BugString); + InbvDisplayString(BugCode); + InbvDisplayString("\r"); break; } } @@ -261,161 +279,663 @@ KeGetBugMessageText(ULONG BugCheckCode, PANSI_STRING OutputString) } VOID -STDCALL +NTAPI KiDoBugCheckCallbacks(VOID) { PKBUGCHECK_CALLBACK_RECORD CurrentRecord; - PLIST_ENTRY ListHead; - - /* FIXME: Check Checksum and add support for WithReason Callbacks */ + PLIST_ENTRY ListHead, NextEntry, LastEntry; + ULONG_PTR Checksum; /* First make sure that the list is Initialized... it might not be */ ListHead = &BugcheckCallbackListHead; - if (ListHead->Flink && ListHead->Blink) { - + if ((ListHead->Flink) && (ListHead->Blink)) + { /* Loop the list */ - LIST_FOR_EACH(CurrentRecord, ListHead, KBUGCHECK_CALLBACK_RECORD, Entry) + LastEntry = ListHead; + NextEntry = ListHead->Flink; + while (NextEntry != ListHead) { - /* Make sure it's inserted */ - if (CurrentRecord->State == BufferInserted) { + /* Get the reord */ + CurrentRecord = CONTAINING_RECORD(NextEntry, + KBUGCHECK_CALLBACK_RECORD, + Entry); + /* Validate it */ + if (CurrentRecord->Entry.Blink != LastEntry) return; + Checksum = (ULONG_PTR)CurrentRecord->CallbackRoutine; + Checksum += (ULONG_PTR)CurrentRecord->Buffer; + Checksum += (ULONG_PTR)CurrentRecord->Length; + Checksum += (ULONG_PTR)CurrentRecord->Component; + + /* Make sure it's inserted and valitdated */ + if ((CurrentRecord->State == BufferInserted) && + (CurrentRecord->Checksum == Checksum)) + { /* Call the routine */ CurrentRecord->State = BufferStarted; (CurrentRecord->CallbackRoutine)(CurrentRecord->Buffer, CurrentRecord->Length); CurrentRecord->State = BufferFinished; } + + /* Go to the next entry */ + LastEntry = NextEntry; + NextEntry = NextEntry->Flink; } } } VOID -STDCALL -KeBugCheckWithTf(ULONG BugCheckCode, - ULONG BugCheckParameter1, - ULONG BugCheckParameter2, - ULONG BugCheckParameter3, - ULONG BugCheckParameter4, - PKTRAP_FRAME Tf) +NTAPI +KiBugCheckDebugBreak(IN ULONG StatusCode) { - KIRQL OldIrql; - BOOLEAN GotExtendedCrashInfo = FALSE; - PVOID Address = 0; - PLDR_DATA_TABLE_ENTRY CurrentModule = NULL; + /* If KDBG isn't connected, freeze the CPU, otherwise, break */ + if (KdDebuggerNotPresent) for (;;) Ke386HaltProcessor(); + DbgBreakPointWithStatus(StatusCode); +} + +PVOID +NTAPI +KiPcToFileHeader(IN PVOID Eip, + OUT PLDR_DATA_TABLE_ENTRY *LdrEntry, + IN BOOLEAN DriversOnly, + OUT PBOOLEAN InKernel) +{ + ULONG i = 0; + PVOID ImageBase, EipBase = NULL; + PLDR_DATA_TABLE_ENTRY Entry; + PLIST_ENTRY ListHead, NextEntry; extern LIST_ENTRY ModuleListHead; -#if 0 - CHAR PrintString[100]; -#endif - /* Make sure we're switching back to the blue screen and print messages on it */ - HalReleaseDisplayOwnership(); - if (!KdpDebugMode.Screen) - { - /* Enable screen debug mode */ - KdpDebugMode.Screen = TRUE; - InitRoutines[0](&DispatchTable[0], 0); - } - /* Try to find out who did this. For this, we need a Trap Frame. - * Note: Some special BSODs pass the Frame/EIP as a Param. MSDN has the - * info so it eventually needs to be supported. - */ - if (Tf) - { - /* For now, get Address from EIP */ - Address = (PVOID)Tf->Eip; + /* Assume no */ + *InKernel = FALSE; - /* Try to get information on the module */ - LIST_FOR_EACH(CurrentModule, &ModuleListHead, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks) + /* Set list pointers and make sure it's valid */ + ListHead = &ModuleListHead; + NextEntry = ListHead->Flink; + if (NextEntry) + { + /* Start loop */ + while (NextEntry != ListHead) { - /* Check if this is the right one */ - if ((Address != NULL && (Address >= (PVOID)CurrentModule->DllBase && - Address < (PVOID)((ULONG_PTR)CurrentModule->DllBase + CurrentModule->SizeOfImage)))) + /* Increase entry */ + i++; + + /* Check if this is a kernel entry and we only want drivers */ + if ((i <= 2) && (DriversOnly == TRUE)) { - /* We got it */ - GotExtendedCrashInfo = TRUE; + /* Skip it */ + NextEntry = NextEntry->Flink; + continue; + } + + /* Get the loader entry */ + Entry = CONTAINING_RECORD(NextEntry, + LDR_DATA_TABLE_ENTRY, + InLoadOrderLinks); + + /* Move to the next entry */ + NextEntry = NextEntry->Flink; + ImageBase = Entry->DllBase; + + /* Check if this is the right one */ + if (((ULONG_PTR)Eip >= (ULONG_PTR)Entry->DllBase) && + ((ULONG_PTR)Eip < ((ULONG_PTR)Entry->DllBase + Entry->SizeOfImage))) + { + /* Return this entry */ + *LdrEntry = Entry; + EipBase = ImageBase; + + /* Check if this was a kernel or HAL entry */ + if (i <= 2) *InKernel = TRUE; break; } } } + /* Return the base address */ + return EipBase; +} + +PCHAR +NTAPI +KeBugCheckUnicodeToAnsi(IN PUNICODE_STRING Unicode, + OUT PCHAR Ansi, + IN ULONG Length) +{ + PCHAR p; + PWCHAR pw; + ULONG i; + + /* Set length and normalize it */ + i = Unicode->Length / sizeof(WCHAR); + i = min(i, Length - 1); + + /* Set source and destination, and copy */ + pw = Unicode->Buffer; + p = Ansi; + while (i--) *p++ = (CHAR)*pw++; + + /* Null terminate and return */ + *p = ANSI_NULL; + return Ansi; +} + +VOID +NTAPI +KiDumpParameterImages(IN PCHAR Message, + IN PULONG_PTR Parameters, + IN ULONG ParameterCount, + IN PKE_BUGCHECK_UNICODE_TO_ANSI ConversionRoutine) +{ + ULONG i; + BOOLEAN InSystem; + PLDR_DATA_TABLE_ENTRY LdrEntry; + PVOID ImageBase; + PUNICODE_STRING DriverName; + CHAR AnsiName[32]; + PIMAGE_NT_HEADERS NtHeader; + ULONG TimeStamp; + BOOLEAN FirstRun = TRUE; + + /* Loop parameters */ + for (i = 0; i < ParameterCount; i++) + { + /* Get the base for this parameter */ + ImageBase = KiPcToFileHeader((PVOID)Parameters[i], + &LdrEntry, + FALSE, + &InSystem); + if (!ImageBase) + { + /* Driver wasn't found, check for unloaded driver */ + DriverName = NULL; // FIXME: ROS can't + if (!DriverName) continue; + + /* Convert the driver name */ + ImageBase = (PVOID)Parameters[i]; + ConversionRoutine(DriverName, AnsiName, sizeof(AnsiName)); + } + else + { + /* Get the NT Headers and Timestamp */ + NtHeader = RtlImageNtHeader(LdrEntry->DllBase); + TimeStamp = NtHeader->FileHeader.TimeDateStamp; + + /* Convert the driver name */ + DriverName = &LdrEntry->BaseDllName; + ConversionRoutine(&LdrEntry->BaseDllName, + AnsiName, + sizeof(AnsiName)); + } + + /* Format driver name */ + sprintf(Message, + "%s** %12s - Address %p base at %p, DateStamp %08lx\n", + FirstRun ? "\r\n*":"*", + AnsiName, + (PVOID)Parameters[i], + ImageBase, + TimeStamp); + + /* Check if we only had one parameter */ + if (ParameterCount <= 1) + { + /* Then just save the name */ + KiBugCheckDriver = DriverName; + } + else + { + /* Otherwise, display the message */ + InbvDisplayString(Message); + } + + /* Loop again */ + FirstRun = FALSE; + } +} + +VOID +NTAPI +KiDisplayBlueScreen(IN ULONG MessageId, + IN BOOLEAN IsHardError, + IN PCHAR HardErrCaption OPTIONAL, + IN PCHAR HardErrMessage OPTIONAL, + IN PCHAR Message) +{ + CHAR AnsiName[75]; + + /* FIXMEs: Use inbv to clear, fill and write to screen. */ + + /* Check if this is a hard error */ + if (IsHardError) + { + /* Display caption and message */ + if (HardErrCaption) InbvDisplayString(HardErrCaption); + if (HardErrMessage) InbvDisplayString(HardErrMessage); + return; + } + + /* Begin the display */ + InbvDisplayString("\r\n"); + + /* Print out initial message */ + KeGetBugMessageText(BUGCHECK_MESSAGE_INTRO, NULL); + InbvDisplayString("\r\n\r\n"); + + /* Check if we have a driver */ + if (KiBugCheckDriver) + { + /* Print out into to driver name */ + KeGetBugMessageText(BUGCODE_ID_DRIVER, NULL); + + /* Convert and print out driver name */ + KeBugCheckUnicodeToAnsi(KiBugCheckDriver, AnsiName, sizeof(AnsiName)); + InbvDisplayString(" "); + InbvDisplayString(AnsiName); + InbvDisplayString("\r\n\r\n"); + } + + /* Check if this is the generic message */ + if (MessageId == BUGCODE_PSS_MESSAGE) + { + /* It is, so get the bug code string as well */ + KeGetBugMessageText(KiBugCheckData[0], NULL); + InbvDisplayString("\r\n\r\n"); + } + + /* Print second introduction message */ + KeGetBugMessageText(PSS_MESSAGE_INTRO, NULL); + InbvDisplayString("\r\n\r\n"); + + /* Get the bug code string */ + KeGetBugMessageText(MessageId, NULL); + InbvDisplayString("\r\n\r\n"); + + /* Print message for technical information */ + KeGetBugMessageText(BUGCHECK_TECH_INFO, NULL); + + /* Show the techincal Data */ + sprintf(AnsiName, + "\r\n\r\n*** STOP: 0x%08lX (0x%p,0x%p,0x%p,0x%p)\r\n\r\n", + KiBugCheckData[0], + (PVOID)KiBugCheckData[1], + (PVOID)KiBugCheckData[2], + (PVOID)KiBugCheckData[3], + (PVOID)KiBugCheckData[4]); + InbvDisplayString(AnsiName); + + /* Check if we have a driver*/ + if (KiBugCheckDriver) + { + /* Display technical driver data */ + InbvDisplayString(Message); + } + else + { + /* Dump parameter information */ + KiDumpParameterImages(Message, + (PVOID)&KiBugCheckData[1], + 4, + KeBugCheckUnicodeToAnsi); + } +} + +VOID +NTAPI +KeBugCheckWithTf(IN ULONG BugCheckCode, + IN ULONG_PTR BugCheckParameter1, + IN ULONG_PTR BugCheckParameter2, + IN ULONG_PTR BugCheckParameter3, + IN ULONG_PTR BugCheckParameter4, + IN PKTRAP_FRAME TrapFrame) +{ + PKPRCB Prcb = KeGetCurrentPrcb(); + CONTEXT Context; + ULONG MessageId; + CHAR AnsiName[128]; + BOOLEAN IsSystem, IsHardError = FALSE; + PCHAR HardErrCaption = NULL, HardErrMessage = NULL; + PVOID Eip = NULL, Memory; + PVOID DriverBase; + PLDR_DATA_TABLE_ENTRY LdrEntry; + PULONG_PTR HardErrorParameters; + KIRQL OldIrql; + + /* Set active bugcheck */ + KeBugCheckActive = TRUE; + KiBugCheckDriver = NULL; + + /* Check if this is power failure simulation */ + if (BugCheckCode == POWER_FAILURE_SIMULATE) + { + /* Call the Callbacks and reboot */; + KiDoBugCheckCallbacks(); + HalReturnToFirmware(HalRebootRoutine); + } + + /* Save the IRQL and set hardware trigger */ + Prcb->DebuggerSavedIRQL = KeGetCurrentIrql(); + InterlockedIncrement(&KiHardwareTrigger); + + /* Capture the CPU Context */ + RtlCaptureContext(&Prcb->ProcessorState.ContextFrame); + Context = Prcb->ProcessorState.ContextFrame; + + /* FIXME: Call the Watchdog if it's regsitered */ + + /* Check which bugcode this is */ + switch (BugCheckCode) + { + /* These bug checks already have detailed messages, keep them */ + case UNEXPECTED_KERNEL_MODE_TRAP: + case DRIVER_CORRUPTED_EXPOOL: + case ACPI_BIOS_ERROR: + case ACPI_BIOS_FATAL_ERROR: + case THREAD_STUCK_IN_DEVICE_DRIVER: + case DATA_BUS_ERROR: + case FAT_FILE_SYSTEM: + case NO_MORE_SYSTEM_PTES: + case INACCESSIBLE_BOOT_DEVICE: + case KMODE_EXCEPTION_NOT_HANDLED: + + /* Keep the same code */ + MessageId = BugCheckCode; + break; + + /* Check if this is a kernel-mode exception */ + case KERNEL_MODE_EXCEPTION_NOT_HANDLED: + + /* Use the generic text message */ + MessageId = KMODE_EXCEPTION_NOT_HANDLED; + + /* File-system errors */ + case NTFS_FILE_SYSTEM: + + /* Use the generic message for FAT */ + MessageId = FAT_FILE_SYSTEM; + + /* Check if this is a coruption of the Mm's Pool */ + case DRIVER_CORRUPTED_MMPOOL: + + /* Use generic corruption message */ + MessageId = DRIVER_CORRUPTED_EXPOOL; + + /* Check if this is a signature check failure */ + case STATUS_SYSTEM_IMAGE_BAD_SIGNATURE: + + /* Use the generic corruption message */ + MessageId = BUGCODE_PSS_MESSAGE_SIGNATURE; + + /* All other codes */ + default: + + /* Use the default bugcheck message */ + MessageId = BUGCODE_PSS_MESSAGE; + } + + /* Save bugcheck data */ + KiBugCheckData[0] = BugCheckCode; + KiBugCheckData[1] = BugCheckParameter1; + KiBugCheckData[2] = BugCheckParameter2; + KiBugCheckData[3] = BugCheckParameter3; + KiBugCheckData[4] = BugCheckParameter4; + + /* Now check what bugcheck this is */ + switch (BugCheckCode) + { + /* Invalid access to R/O memory or Unhandled KM Exception */ + case KERNEL_MODE_EXCEPTION_NOT_HANDLED: + case ATTEMPTED_WRITE_TO_READONLY_MEMORY: + case ATTEMPTED_EXECUTE_OF_NOEXECUTE_MEMORY: + + /* Check if we have a trap frame */ + if (!TrapFrame) + { + /* Use parameter 3 as a trap frame, if it exists */ + if (BugCheckParameter3) TrapFrame = (PVOID)BugCheckParameter3; + } + + /* Check if we got one now and if we need to get EIP */ + if ((TrapFrame) && + (BugCheckCode != KERNEL_MODE_EXCEPTION_NOT_HANDLED)) + { + /* Get EIP */ + Eip = (PVOID)TrapFrame->Eip; + } + break; + + /* Wrong IRQL */ + case IRQL_NOT_LESS_OR_EQUAL: + + /* + * The NT kernel has 3 special sections: + * MISYSPTE, POOLMI and POOLCODE. The bug check code can + * determine in which of these sections this bugcode happened + * and provide a more detailed analysis. For now, we don't. + */ + + /* Eip is in parameter 4 */ + Eip = (PVOID)BugCheckParameter4; + + /* Get the driver base */ + DriverBase = KiPcToFileHeader(Eip, &LdrEntry, FALSE, &IsSystem); + if (IsSystem) + { + /* + * The error happened inside the kernel or HAL. + * Get the memory address that was being referenced. + */ + Memory = (PVOID)BugCheckParameter1; + + /* Find to which driver it belongs */ + DriverBase = KiPcToFileHeader(Memory, + &LdrEntry, + TRUE, + &IsSystem); + if (DriverBase) + { + /* Get the driver name and update the bug code */ + KiBugCheckDriver = &LdrEntry->BaseDllName; + KiBugCheckData[0] = DRIVER_PORTION_MUST_BE_NONPAGED; + } + else + { + /* Find the driver that unloaded at this address */ + KiBugCheckDriver = NULL; // FIXME: ROS can't locate + + /* Check if the cause was an unloaded driver */ + if (KiBugCheckDriver) + { + /* Update bug check code */ + KiBugCheckData[0] = + SYSTEM_SCAN_AT_RAISED_IRQL_CAUGHT_IMPROPER_DRIVER_UNLOAD; + } + } + } + else + { + /* Update the bug check code */ + KiBugCheckData[0] = DRIVER_IRQL_NOT_LESS_OR_EQUAL; + } + + /* Clear EIP so we don't look it up later */ + Eip = NULL; + break; + + /* Hard error */ + case FATAL_UNHANDLED_HARD_ERROR: + + /* Copy bug check data from hard error */ + HardErrorParameters = (PULONG_PTR)BugCheckParameter2; + KiBugCheckData[0] = BugCheckParameter1; + KiBugCheckData[1] = HardErrorParameters[0]; + KiBugCheckData[2] = HardErrorParameters[1]; + KiBugCheckData[3] = HardErrorParameters[2]; + KiBugCheckData[4] = HardErrorParameters[3]; + + /* Remember that this is hard error and set the caption/message */ + IsHardError = TRUE; + HardErrCaption = (PCHAR)BugCheckParameter3; + HardErrMessage = (PCHAR)BugCheckParameter4; + break; + + /* Page fault */ + case PAGE_FAULT_IN_NONPAGED_AREA: + + /* Assume no driver */ + DriverBase = NULL; + + /* Check if we have a trap frame */ + if (!TrapFrame) + { + /* We don't, use parameter 3 if possible */ + if (BugCheckParameter3) TrapFrame = (PVOID)BugCheckParameter3; + } + + /* Check if we have a frame now */ + if (TrapFrame) + { + /* Get EIP */ + Eip = (PVOID)TrapFrame->Eip; + + /* Find out if was in the kernel or drivers */ + DriverBase = KiPcToFileHeader(Eip, &LdrEntry, FALSE, &IsSystem); + } + + /* + * Now we should check if this happened in: + * 1) Special Pool 2) Free Special Pool 3) Session Pool + * and update the bugcheck code appropriately. + */ + + /* Check if we had a driver base */ + if (DriverBase) + { + /* Find the driver that unloaded at this address */ + KiBugCheckDriver = NULL; // FIXME: ROS can't locate + + /* Check if the cause was an unloaded driver */ + if (KiBugCheckDriver) + { + KiBugCheckData[0] = + DRIVER_UNLOADED_WITHOUT_CANCELLING_PENDING_OPERATIONS; + } + } + break; + + /* Check if the driver forgot to unlock pages */ + case DRIVER_LEFT_LOCKED_PAGES_IN_PROCESS: + + /* EIP is in parameter 1 */ + Eip = (PVOID)BugCheckParameter1; + break; + + /* Check if the driver consumed too many PTEs */ + case DRIVER_USED_EXCESSIVE_PTES: + + /* Driver base is in parameter 1 */ + DriverBase = (PVOID)BugCheckParameter1; + KiBugCheckDriver = &LdrEntry->BaseDllName; + break; + + /* Check if the driver has a stuck thread */ + case THREAD_STUCK_IN_DEVICE_DRIVER: + + /* The name is in Parameter 3 */ + KiBugCheckDriver = (PVOID)BugCheckParameter3; + break; + + /* Anything else */ + default: + break; + } + + /* Do we have a driver name? */ + if (KiBugCheckDriver) + { + /* Convert it to ANSI */ + KeBugCheckUnicodeToAnsi(KiBugCheckDriver, AnsiName, sizeof(AnsiName)); + } + else + { + /* Do we have an EIP? */ + if (Eip) + { + /* Dump image name */ + KiDumpParameterImages(AnsiName, + (PULONG_PTR)&Eip, + 1, + KeBugCheckUnicodeToAnsi); + } + } + + /* FIXME: Check if we need to save the context for KD */ + + /* Check if a debugger is connected */ + if ((BugCheckCode != MANUALLY_INITIATED_CRASH) && (KdDebuggerEnabled)) + { + /* Crash on the debugger console */ + DbgPrint("\n*** Fatal System Error: 0x%08lx\n" + " (0x%p,0x%p,0x%p,0x%p)\n\n", + KiBugCheckData[0], + KiBugCheckData[1], + KiBugCheckData[2], + KiBugCheckData[3], + KiBugCheckData[4]); + + /* Check if the debugger isn't currently connected */ + if (!KdDebuggerNotPresent) + { + /* Check if we have a driver to blame */ + if (KiBugCheckDriver) + { + /* Dump it */ + DbgPrint("Driver at fault: %s.\n", AnsiName); + } + + /* Check if this was a hard error */ + if (IsHardError) + { + /* Print caption and message */ + if (HardErrCaption) DbgPrint(HardErrCaption); + if (HardErrMessage) DbgPrint(HardErrMessage); + } + + /* Break in the debugger */ + KiBugCheckDebugBreak(DBG_STATUS_BUGCHECK_FIRST); + } + else + { + /* + * ROS HACK. + * Ok, so debugging is enabled, but KDBG isn't there. + * We'll manually dump the stack for the user. + */ + KeRosDumpStackFrames(NULL, 0); + } + } + + /* Switching back to the blue screen so we print messages on it */ + HalReleaseDisplayOwnership(); + /* Raise IRQL to HIGH_LEVEL */ Ke386DisableInterrupts(); KeRaiseIrql(HIGH_LEVEL, &OldIrql); - /* Unload the Kernel Adress Space if we own it */ + /* Unlock the Kernel Adress Space if we own it */ if (KernelAddressSpaceLock.Owner == KeGetCurrentThread()) + { MmUnlockAddressSpace(MmGetKernelAddressSpace()); - - /* FIXMEs: Use inbv to clear, fill and write to screen. */ - - /* Show the STOP Message */ -#if 0 - InbvDisplayString("A problem has been detected and ReactOS has been shut down to prevent " - "damage to your computer.\n\n"); -#else - DbgPrint("A problem has been detected and ReactOS has been shut down to prevent " - "damage to your computer.\n\n"); -#endif - /* Show the module name of who caused this */ - if (GotExtendedCrashInfo) - { -#if 0 - sprintf(PrintString, - "The problem seems to be caused by the following file: %wZ\n\n", - &CurrentModule->BaseDllName); - InbvDisplayString(PrintString); -#else - DbgPrint("The problem seems to be caused by the following file: %wZ\n\n", - &CurrentModule->BaseDllName); -#endif } - /* Find the Bug Code String */ - KeGetBugMessageText(BugCheckCode, NULL); - - /* Show the techincal Data */ -#if 0 - sprintf(PrintString, - "Technical information:\n\n*** STOP: 0x%08lX (0x%p,0x%p,0x%p,0x%p)\n\n", - BugCheckCode, - (PVOID)BugCheckParameter1, - (PVOID)BugCheckParameter2, - (PVOID)BugCheckParameter3, - (PVOID)BugCheckParameter4); - InbvDisplayString(PrintString); -#else - DbgPrint("Technical information:\n\n*** STOP: 0x%08lX (0x%p,0x%p,0x%p,0x%p)\n\n", - BugCheckCode, - (PVOID)BugCheckParameter1, - (PVOID)BugCheckParameter2, - (PVOID)BugCheckParameter3, - (PVOID)BugCheckParameter4); -#endif - /* Show the module name and more data of who caused this */ - if (GotExtendedCrashInfo) + /* Avoid recursion */ + if (!InterlockedDecrement(&KeBugCheckCount)) { -#if 0 - sprintf(PrintString, - "*** %wZ - Address 0x%p base at 0x%p, DateStamp 0x%x\n\n", - &CurrentModule->BaseDllName, - Address, - (PVOID)CurrentModule->DllBase, - 0); - InbvDisplayString(PrintString); -#else - DbgPrint("*** %wZ - Address 0x%p base at 0x%p, DateStamp 0x%x\n\n", - &CurrentModule->BaseDllName, - Address, - (PVOID)CurrentModule->DllBase, - 0); -#endif - } + /* Set CPU that is bug checking now */ + KeBugCheckOwner = Prcb->Number; - /* There can only be one Bugcheck per Bootup */ - if (!InterlockedDecrement((PLONG)&KeBugCheckCount)) - { #ifdef CONFIG_SMP - LONG i; /* Freeze the other CPUs */ for (i = 0; i < KeNumberProcessors; i++) { @@ -427,69 +947,194 @@ KeBugCheckWithTf(ULONG BugCheckCode, } } #endif - /* Check if we got a Trap Frame */ - if (Tf) - { - /* Dump it */ - KiDumpTrapFrame(Tf, BugCheckParameter1, BugCheckParameter2); - } - else - { - /* We can only dump the frames */ -#if defined(__GNUC__) - KeDumpStackFrames((PULONG)__builtin_frame_address(0)); -#elif defined(_MSC_VER) - __asm push ebp - __asm call KeDumpStackFrames - __asm add esp, 4 -#else -#error Unknown compiler for inline assembler -#endif - } - /* Call the Callbacks */; - KiDoBugCheckCallbacks(); + /* Display the BSOD */ + KiDisplayBlueScreen(MessageId, + IsHardError, + HardErrCaption, + HardErrMessage, + AnsiName); - /* Dump the BSOD to the Paging File */ - MmDumpToPagingFile(BugCheckCode, - BugCheckParameter1, - BugCheckParameter2, - BugCheckParameter3, - BugCheckParameter4, - Tf); + /* FIXME: Enable debugger if it was pending */ - /* Wake up the Debugger */ - if (KdDebuggerEnabled) - { - Ke386EnableInterrupts(); - DbgBreakPointWithStatus(DBG_STATUS_BUGCHECK_SECOND); - Ke386DisableInterrupts(); - } + /* Print the last line */ + InbvDisplayString("\r\n"); + + /* Save the context */ + Prcb->ProcessorState.ContextFrame = Context; + + /* FIXME: Support Triage Dump */ + + /* Write the crash dump */ + MmDumpToPagingFile(KiBugCheckData[4], + KiBugCheckData[0], + KiBugCheckData[1], + KiBugCheckData[2], + KiBugCheckData[3], + TrapFrame); } - /* Halt this CPU now */ - for (;;) Ke386HaltProcessor(); + /* Increase recursioun count */ + KeBugCheckOwnerRecursionCount++; + if (KeBugCheckOwnerRecursionCount == 2) + { + /* Break in the debugger */ + KiBugCheckDebugBreak(DBG_STATUS_BUGCHECK_SECOND); + } + else if (KeBugCheckOwnerRecursionCount > 2) + { + /* Halt the CPU */ + for (;;) Ke386HaltProcessor(); + } + + /* Call the Callbacks */ + KiDoBugCheckCallbacks(); + + /* FIXME: Call Watchdog if enabled */ + + /* Attempt to break in the debugger (otherwise halt CPU) */ + KiBugCheckDebugBreak(DBG_STATUS_BUGCHECK_SECOND); +} + +/* PUBLIC FUNCTIONS **********************************************************/ + +/* + * @implemented + */ +BOOLEAN +NTAPI +KeDeregisterBugCheckCallback(IN PKBUGCHECK_CALLBACK_RECORD CallbackRecord) +{ + KIRQL OldIrql; + BOOLEAN Status = FALSE; + + /* Raise IRQL to High */ + KeRaiseIrql(HIGH_LEVEL, &OldIrql); + + /* Check the Current State */ + if (CallbackRecord->State == BufferInserted) + { + /* Reset state and remove from list */ + CallbackRecord->State = BufferEmpty; + RemoveEntryList(&CallbackRecord->Entry); + Status = TRUE; + } + + /* Lower IRQL and return */ + KeLowerIrql(OldIrql); + return Status; +} + +/* + * @implemented + */ +BOOLEAN +NTAPI +KeDeregisterBugCheckReasonCallback( + IN PKBUGCHECK_REASON_CALLBACK_RECORD CallbackRecord) +{ + KIRQL OldIrql; + BOOLEAN Status = FALSE; + + /* Raise IRQL to High */ + KeRaiseIrql(HIGH_LEVEL, &OldIrql); + + /* Check the Current State */ + if (CallbackRecord->State == BufferInserted) + { + /* Reset state and remove from list */ + CallbackRecord->State = BufferEmpty; + RemoveEntryList(&CallbackRecord->Entry); + Status = TRUE; + } + + /* Lower IRQL and return */ + KeLowerIrql(OldIrql); + return Status; +} + +/* + * @implemented + */ +BOOLEAN +NTAPI +KeRegisterBugCheckCallback(IN PKBUGCHECK_CALLBACK_RECORD CallbackRecord, + IN PKBUGCHECK_CALLBACK_ROUTINE CallbackRoutine, + IN PVOID Buffer, + IN ULONG Length, + IN PUCHAR Component) +{ + KIRQL OldIrql; + BOOLEAN Status = FALSE; + + /* Raise IRQL to High */ + KeRaiseIrql(HIGH_LEVEL, &OldIrql); + + /* Check the Current State first so we don't double-register */ + if (CallbackRecord->State == BufferEmpty) + { + /* Set the Callback Settings and insert into the list */ + CallbackRecord->Length = Length; + CallbackRecord->Buffer = Buffer; + CallbackRecord->Component = Component; + CallbackRecord->CallbackRoutine = CallbackRoutine; + CallbackRecord->State = BufferInserted; + InsertTailList(&BugcheckCallbackListHead, &CallbackRecord->Entry); + Status = TRUE; + } + + /* Lower IRQL and return */ + KeLowerIrql(OldIrql); + return Status; +} + +/* + * @implemented + */ +BOOLEAN +NTAPI +KeRegisterBugCheckReasonCallback( + IN PKBUGCHECK_REASON_CALLBACK_RECORD CallbackRecord, + IN PKBUGCHECK_REASON_CALLBACK_ROUTINE CallbackRoutine, + IN KBUGCHECK_CALLBACK_REASON Reason, + IN PUCHAR Component) +{ + KIRQL OldIrql; + BOOLEAN Status = FALSE; + + /* Raise IRQL to High */ + KeRaiseIrql(HIGH_LEVEL, &OldIrql); + + /* Check the Current State first so we don't double-register */ + if (CallbackRecord->State == BufferEmpty) + { + /* Set the Callback Settings and insert into the list */ + CallbackRecord->Component = Component; + CallbackRecord->CallbackRoutine = CallbackRoutine; + CallbackRecord->State = BufferInserted; + CallbackRecord->Reason = Reason; + InsertTailList(&BugcheckReasonCallbackListHead, + &CallbackRecord->Entry); + Status = TRUE; + } + + /* Lower IRQL and return */ + KeLowerIrql(OldIrql); + return Status; } /* * @implemented - * - * FUNCTION: Brings the system down in a controlled manner when an - * inconsistency that might otherwise cause corruption has been detected - * ARGUMENTS: - * BugCheckCode = Specifies the reason for the bug check - * BugCheckParameter[1-4] = Additional information about bug - * RETURNS: Doesn't */ VOID -STDCALL -KeBugCheckEx(ULONG BugCheckCode, - ULONG BugCheckParameter1, - ULONG BugCheckParameter2, - ULONG BugCheckParameter3, - ULONG BugCheckParameter4) +NTAPI +KeBugCheckEx(IN ULONG BugCheckCode, + IN ULONG_PTR BugCheckParameter1, + IN ULONG_PTR BugCheckParameter2, + IN ULONG_PTR BugCheckParameter3, + IN ULONG_PTR BugCheckParameter4) { - /* Call the Trap Frame version without a Trap Frame */ + /* Call the internal API */ KeBugCheckWithTf(BugCheckCode, BugCheckParameter1, BugCheckParameter2, @@ -500,18 +1145,13 @@ KeBugCheckEx(ULONG BugCheckCode, /* * @implemented - * - * FUNCTION: Brings the system down in a controlled manner when an - * inconsistency that might otherwise cause corruption has been detected - * ARGUMENTS: - * BugCheckCode = Specifies the reason for the bug check - * RETURNS: Doesn't */ VOID -STDCALL +NTAPI KeBugCheck(ULONG BugCheckCode) { - KeBugCheckEx(BugCheckCode, 0, 0, 0, 0); + /* Call the internal API */ + KeBugCheckWithTf(BugCheckCode, 0, 0, 0, 0, NULL); } /* EOF */ diff --git a/reactos/ntoskrnl/ke/i386/exp.c b/reactos/ntoskrnl/ke/i386/exp.c index 98fabbba000..56b0bb00bd5 100644 --- a/reactos/ntoskrnl/ke/i386/exp.c +++ b/reactos/ntoskrnl/ke/i386/exp.c @@ -1,214 +1,40 @@ /* - * COPYRIGHT: See COPYING in the top level directory * PROJECT: ReactOS Kernel + * LICENSE: GPL - See COPYING in the top level directory * FILE: ntoskrnl/ke/i386/exp.c - * PURPOSE: Exception Support Code - * PROGRAMMERS: Alex Ionescu (alex@relsoft.net) + * PURPOSE: Exception Dispatching and Context<->Trap Frame Conversion + * PROGRAMMERS: Alex Ionescu (alex.ionescu@reactos.org) * Gregor Anich - * David Welch (welch@cwcom.net) * Skywing (skywing@valhallalegends.com) */ -/* INCLUDES *****************************************************************/ +/* INCLUDES ******************************************************************/ #include - #define NDEBUG -#include +#include -#if defined (ALLOC_PRAGMA) -#pragma alloc_text(INIT, KeInitExceptions) -#endif - -#define SIZE_OF_FX_REGISTERS 32 +/* FUNCTIONS *****************************************************************/ VOID +INIT_FUNCTION NTAPI -Ki386AdjustEsp0( - IN PKTRAP_FRAME TrapFrame -); - -VOID -NTAPI -KiFlushNPXState( - IN FLOATING_SAVE_AREA *SaveArea -); - -extern KIDTENTRY KiIdt[]; - -/* GLOBALS *****************************************************************/ - -#define FLAG_IF (1<<9) - -#define _STR(x) #x -#define STR(x) _STR(x) - -#ifndef ARRAY_SIZE -# define ARRAY_SIZE(x) (sizeof (x) / sizeof (x[0])) -#endif - -extern ULONG init_stack; -extern ULONG init_stack_top; - -extern BOOLEAN Ke386NoExecute; - -static char *ExceptionTypeStrings[] = - { - "Divide Error", - "Debug Trap", - "NMI", - "Breakpoint", - "Overflow", - "BOUND range exceeded", - "Invalid Opcode", - "No Math Coprocessor", - "Double Fault", - "Unknown(9)", - "Invalid TSS", - "Segment Not Present", - "Stack Segment Fault", - "General Protection", - "Page Fault", - "Reserved(15)", - "Math Fault", - "Alignment Check", - "Machine Check", - "SIMD Fault" - }; - -NTSTATUS ExceptionToNtStatus[] = - { - STATUS_INTEGER_DIVIDE_BY_ZERO, - STATUS_SINGLE_STEP, - STATUS_ACCESS_VIOLATION, - STATUS_BREAKPOINT, - STATUS_INTEGER_OVERFLOW, - STATUS_ARRAY_BOUNDS_EXCEEDED, - STATUS_ILLEGAL_INSTRUCTION, - STATUS_FLOAT_INVALID_OPERATION, - STATUS_ACCESS_VIOLATION, - STATUS_ACCESS_VIOLATION, - STATUS_ACCESS_VIOLATION, - STATUS_ACCESS_VIOLATION, - STATUS_STACK_OVERFLOW, - STATUS_ACCESS_VIOLATION, - STATUS_ACCESS_VIOLATION, - STATUS_ACCESS_VIOLATION, /* RESERVED */ - STATUS_FLOAT_INVALID_OPERATION, /* Should not be used, the FPU can give more specific info */ - STATUS_DATATYPE_MISALIGNMENT, - STATUS_ACCESS_VIOLATION, - STATUS_FLOAT_MULTIPLE_TRAPS, - }; - -/* FUNCTIONS ****************************************************************/ - -BOOLEAN STDCALL -KiRosPrintAddress(PVOID address) +KeInitExceptions(VOID) { - PLIST_ENTRY current_entry; - PLDR_DATA_TABLE_ENTRY current; - extern LIST_ENTRY ModuleListHead; - ULONG_PTR RelativeAddress; - ULONG i = 0; + ULONG i; + USHORT FlippedSelector; + extern KIDTENTRY KiIdt[]; - do - { - current_entry = ModuleListHead.Flink; + /* Loop the IDT */ + for (i = 0; i <= MAXIMUM_IDTVECTOR; i ++) + { + /* Save the current Selector */ + FlippedSelector = KiIdt[i].Selector; - while (current_entry != &ModuleListHead) - { - current = - CONTAINING_RECORD(current_entry, LDR_DATA_TABLE_ENTRY, InLoadOrderLinks); - - if (address >= (PVOID)current->DllBase && - address < (PVOID)((ULONG_PTR)current->DllBase + current->SizeOfImage)) - { - RelativeAddress = (ULONG_PTR) address - (ULONG_PTR) current->DllBase; - DbgPrint("<%wZ: %x>", ¤t->FullDllName, RelativeAddress); - return(TRUE); - } - current_entry = current_entry->Flink; - } - - address = (PVOID)((ULONG_PTR)address & ~(ULONG_PTR)MmSystemRangeStart); - } while(++i <= 1); - - return(FALSE); -} - -VOID -NTAPI -KiDumpTrapFrame(PKTRAP_FRAME Tf, ULONG Parameter1, ULONG Parameter2) -{ - ULONG cr3_; - ULONG StackLimit; - ULONG Esp0; - ULONG ExceptionNr = (ULONG)Tf->DbgArgMark; - ULONG cr2 = (ULONG)Tf->DbgArgPointer; - - Esp0 = (ULONG)Tf; - - /* - * Print out the CPU registers - */ - if (ExceptionNr < ARRAY_SIZE(ExceptionTypeStrings)) - { - DbgPrint("%s Exception: %d(%x)\n", ExceptionTypeStrings[ExceptionNr], - ExceptionNr, Tf->ErrCode&0xffff); - } - else - { - DbgPrint("Exception: %d(%x)\n", ExceptionNr, Tf->ErrCode&0xffff); - } - DbgPrint("Processor: %d CS:EIP %x:%x ", KeGetCurrentProcessorNumber(), - Tf->SegCs&0xffff, Tf->Eip); - KeRosPrintAddress((PVOID)Tf->Eip); - DbgPrint("\n"); - Ke386GetPageTableDirectory(cr3_); - DbgPrint("cr2 %x cr3 %x ", cr2, cr3_); - DbgPrint("Proc: %x ",PsGetCurrentProcess()); - if (PsGetCurrentProcess() != NULL) - { - DbgPrint("Pid: %x <", PsGetCurrentProcess()->UniqueProcessId); - DbgPrint("%.16s> ", PsGetCurrentProcess()->ImageFileName); - } - if (PsGetCurrentThread() != NULL) - { - DbgPrint("Thrd: %x Tid: %x", - PsGetCurrentThread(), - PsGetCurrentThread()->Cid.UniqueThread); - } - DbgPrint("\n"); - DbgPrint("DS %x ES %x FS %x GS %x\n", Tf->SegDs&0xffff, Tf->SegEs&0xffff, - Tf->SegFs&0xffff, Tf->SegGs&0xfff); - DbgPrint("EAX: %.8x EBX: %.8x ECX: %.8x\n", Tf->Eax, Tf->Ebx, Tf->Ecx); - DbgPrint("EDX: %.8x EBP: %.8x ESI: %.8x ESP: %.8x\n", Tf->Edx, - Tf->Ebp, Tf->Esi, Esp0); - DbgPrint("EDI: %.8x EFLAGS: %.8x ", Tf->Edi, Tf->EFlags); - if ((Tf->SegCs&0xffff) == KGDT_R0_CODE) - { - DbgPrint("kESP %.8x ", Esp0); - if (PsGetCurrentThread() != NULL) - { - DbgPrint("kernel stack base %x\n", - PsGetCurrentThread()->Tcb.StackLimit); - - } - } - - if (PsGetCurrentThread() != NULL) - { - StackLimit = (ULONG)PsGetCurrentThread()->Tcb.StackBase; - } - else - { - StackLimit = (ULONG)init_stack_top; - } - - /* - * Dump the stack frames - */ - KeDumpStackFrames((PULONG)Tf->Ebp); + /* Flip Selector and Extended Offset */ + KiIdt[i].Selector = KiIdt[i].ExtendedOffset; + KiIdt[i].ExtendedOffset = FlippedSelector; + } } ULONG @@ -750,177 +576,6 @@ KeTrapFrameToContext(IN PKTRAP_FRAME TrapFrame, if (OldIrql < APC_LEVEL) KeLowerIrql(OldIrql); } -VOID -NTAPI -KeDumpStackFrames(PULONG Frame) -{ - PULONG StackBase, StackEnd; - MEMORY_BASIC_INFORMATION mbi; - ULONG ResultLength = sizeof(mbi); - NTSTATUS Status; - - DbgPrint("Frames:\n"); - _SEH_TRY - { - Status = MiQueryVirtualMemory ( - (HANDLE)-1, - Frame, - MemoryBasicInformation, - &mbi, - sizeof(mbi), - &ResultLength ); - if ( !NT_SUCCESS(Status) ) - { - DPRINT1("Can't dump stack frames: MiQueryVirtualMemory() failed: %x\n", Status ); - return; - } - - StackBase = Frame; - StackEnd = (PULONG)((ULONG_PTR)mbi.BaseAddress + mbi.RegionSize); - - while ( Frame >= StackBase && Frame < StackEnd ) - { - ULONG Addr = Frame[1]; - if (!KeRosPrintAddress((PVOID)Addr)) - DbgPrint("<%X>", Addr); - if ( Addr == 0 || Addr == 0xDEADBEEF ) - break; - StackBase = Frame; - Frame = (PULONG)Frame[0]; - DbgPrint("\n"); - } - } - _SEH_HANDLE - { - } - _SEH_END; - DbgPrint("\n"); -} - -VOID STDCALL -KeRosDumpStackFrames ( PULONG Frame, ULONG FrameCount ) -{ - ULONG i=0; - PULONG StackBase, StackEnd; - MEMORY_BASIC_INFORMATION mbi; - ULONG ResultLength = sizeof(mbi); - NTSTATUS Status; - - DbgPrint("Frames: "); - _SEH_TRY - { - if ( !Frame ) - { -#if defined __GNUC__ - __asm__("mov %%ebp, %0" : "=r" (Frame) : ); -#elif defined(_MSC_VER) - __asm mov [Frame], ebp -#endif - //Frame = (PULONG)Frame[0]; // step out of KeRosDumpStackFrames - } - - Status = MiQueryVirtualMemory ( - (HANDLE)-1, - Frame, - MemoryBasicInformation, - &mbi, - sizeof(mbi), - &ResultLength ); - if ( !NT_SUCCESS(Status) ) - { - DPRINT1("Can't dump stack frames: MiQueryVirtualMemory() failed: %x\n", Status ); - return; - } - - StackBase = Frame; - StackEnd = (PULONG)((ULONG_PTR)mbi.BaseAddress + mbi.RegionSize); - - while ( Frame >= StackBase && Frame < StackEnd && i++ < FrameCount ) - { - ULONG Addr = Frame[1]; - if (!KeRosPrintAddress((PVOID)Addr)) - DbgPrint("<%X>", Addr); - if ( Addr == 0 || Addr == 0xDEADBEEF ) - break; - StackBase = Frame; - Frame = (PULONG)Frame[0]; - DbgPrint(" "); - } - } - _SEH_HANDLE - { - } - _SEH_END; - DbgPrint("\n"); -} - -ULONG STDCALL -KeRosGetStackFrames ( PULONG Frames, ULONG FrameCount ) -{ - ULONG Count = 0; - PULONG StackBase, StackEnd, Frame; - MEMORY_BASIC_INFORMATION mbi; - ULONG ResultLength = sizeof(mbi); - NTSTATUS Status; - - _SEH_TRY - { -#if defined __GNUC__ - __asm__("mov %%ebp, %0" : "=r" (Frame) : ); -#elif defined(_MSC_VER) - __asm mov [Frame], ebp -#endif - - Status = MiQueryVirtualMemory ( - (HANDLE)-1, - Frame, - MemoryBasicInformation, - &mbi, - sizeof(mbi), - &ResultLength ); - if ( !NT_SUCCESS(Status) ) - { - DPRINT1("Can't get stack frames: MiQueryVirtualMemory() failed: %x\n", Status ); - return 0; - } - - StackBase = Frame; - StackEnd = (PULONG)((ULONG_PTR)mbi.BaseAddress + mbi.RegionSize); - - while ( Count < FrameCount && Frame >= StackBase && Frame < StackEnd ) - { - Frames[Count++] = Frame[1]; - StackBase = Frame; - Frame = (PULONG)Frame[0]; - } - } - _SEH_HANDLE - { - } - _SEH_END; - return Count; -} - -VOID -INIT_FUNCTION -NTAPI -KeInitExceptions(VOID) -{ - ULONG i; - USHORT FlippedSelector; - - /* Loop the IDT */ - for (i = 0; i <= MAXIMUM_IDTVECTOR; i ++) - { - /* Save the current Selector */ - FlippedSelector = KiIdt[i].Selector; - - /* Flip Selector and Extended Offset */ - KiIdt[i].Selector = KiIdt[i].ExtendedOffset; - KiIdt[i].ExtendedOffset = FlippedSelector; - } -} - VOID NTAPI KiDispatchException(PEXCEPTION_RECORD ExceptionRecord, @@ -1091,10 +746,10 @@ NTSTATUS NTAPI KeRaiseUserException(IN NTSTATUS ExceptionCode) { - ULONG OldEip; - PKTHREAD Thread = KeGetCurrentThread(); + ULONG OldEip; + PKTHREAD Thread = KeGetCurrentThread(); - /* Make sure we can access the TEB */ + /* Make sure we can access the TEB */ _SEH_TRY { Thread->Teb->ExceptionCode = ExceptionCode; diff --git a/reactos/ntoskrnl/ke/i386/v86vdm.c b/reactos/ntoskrnl/ke/i386/v86vdm.c index 357ceb085e6..733ae101db2 100644 --- a/reactos/ntoskrnl/ke/i386/v86vdm.c +++ b/reactos/ntoskrnl/ke/i386/v86vdm.c @@ -86,7 +86,8 @@ Ke386CallBios(IN ULONG Int, KeSetSystemAffinityThread(1); /* Make sure there's space for two IOPMs, then copy & clear the current */ - //ASSERT(((PKGDTENTRY)&KeGetPcr()->GDT[KGDT_TSS / 8])->LimitLow >= (0x2000 + IOPM_OFFSET - 1)); + //ASSERT(((PKGDTENTRY)&KeGetPcr()->GDT[KGDT_TSS / 8])->LimitLow >= + // (0x2000 + IOPM_OFFSET - 1)); RtlMoveMemory(Ki386IopmSaveArea, &Tss->IoMaps[0].IoMap, PAGE_SIZE * 2); RtlZeroMemory(&Tss->IoMaps[0].IoMap, PAGE_SIZE * 2); diff --git a/reactos/ntoskrnl/ntoskrnl.mc b/reactos/ntoskrnl/ntoskrnl.mc index 0a035c2e51e..dd1ff9a8da5 100644 --- a/reactos/ntoskrnl/ntoskrnl.mc +++ b/reactos/ntoskrnl/ntoskrnl.mc @@ -21,6 +21,58 @@ LanguageNames=(English=0x409:MSG00409) ; ; message definitions ; +MessageId=0x7F +Severity=Warning +Facility=System +SymbolicName=BUGCHECK_MESSAGE_INTRO +Language=English +A problem has been detected and ReactOS has been shut down to prevent damage +to your computer. +. + +MessageId=0x80 +Severity=Warning +Facility=System +SymbolicName=BUGCODE_ID_DRIVER +Language=English +The problem seems to be caused by the following file: + +. + +MessageId=0x81 +Severity=Warning +Facility=System +SymbolicName=PSS_MESSAGE_INTRO +Language=English +If this is the first time you've seen this Stop error screen, +restart your computer. If this screen appears again, follow +these steps: + +. + +MessageId=0x82 +Severity=Warning +Facility=System +SymbolicName=BUGCODE_PSS_MESSAGE +Language=English +Check to make sure any new hardware or software is properly installed. +If this is a new installation, ask your hardware or software manufacturer +for any ReactOS updates you might need. + +If problems continue, disable or remove any newly installed hardware +or software. Disable BIOS memory options such as caching or shadowing. +If you need to use Safe Mode to remove or disable components, restart +your computer, press F8 to select Advanced Startup Options, and then +select Safe Mode. +. + +MessageId=0x83 +Severity=Warning +Facility=System +SymbolicName=BUGCHECK_TECH_INFO +Language=English +Technical information: +. MessageId=0x0 Severity=Success @@ -267,7 +319,16 @@ Severity=Success Facility=System SymbolicName=KMODE_EXCEPTION_NOT_HANDLED Language=English -KMODE_EXCEPTION_NOT_HANDLED +Check to be sure you have adequate disk space. If a driver is +identified in the Stop message, disable the driver or check +with the manufacturer for driver updates. Try changing video +adapters. + +Check with your hardware vendor for any BIOS updates. Disable +BIOS memory options such as caching or shadowing. If you need +to use Safe Mode to remove or disable components, restart your +computer, press F8 to select Advanced Startup Options, and then +select Safe Mode. . MessageId=0x1F @@ -307,7 +368,10 @@ Severity=Success Facility=System SymbolicName=FAT_FILE_SYSTEM Language=English -FAT_FILE_SYSTEM +Disable or uninstall any anti-virus, disk defragmentation +or backup utilities. Check your hard drive configuration, +and check for any updated drivers. Run CHKDSK /F to check +for hard drive corruption, and then restart your computer. . MessageId=0x24 @@ -395,7 +459,15 @@ Severity=Success Facility=System SymbolicName=DATA_BUS_ERROR Language=English -DATA_BUS_ERROR +Run system diagnostics supplied by your hardware manufacturer. +In particular, run a memory check, and check for faulty or +mismatched memory. Try changing video adapters. + +Check with your hardware vendor for any BIOS updates. Disable +BIOS memory options such as caching or shadowing. If you need +to use Safe Mode to remove or disable components, restart your +computer, press F8 to select Advanced Startup Options, and then +select Safe Mode. . MessageId=0x2F @@ -502,7 +574,12 @@ Severity=Success Facility=System SymbolicName=NO_MORE_SYSTEM_PTES Language=English -NO_MORE_SYSTEM_PTES +Remove any recently installed software including backup +utilities or disk-intensive applications. + +If you need to use Safe Mode to remove or disable components, +restart your computer, press F8 to select Advanced Startup +Options, and then select Safe Mode. . MessageId=0x40 @@ -581,7 +658,13 @@ Language=English STREAMS_INTERNAL_ERROR . - +MessageId=0x4C +Severity=Success +Facility=System +SymbolicName=FATAL_UNHANDLED_HARD_ERROR +Language=English +FATAL_UNHANDLED_HARD_ERROR +. MessageId=0x4D Severity=Success @@ -942,7 +1025,11 @@ Severity=Success Facility=System SymbolicName=INACCESSIBLE_BOOT_DEVICE Language=English -INACCESSIBLE_BOOT_DEVICE +Check for viruses on your computer. Remove any newly installed +hard drives or hard drive controllers. Check your hard drive +to make sure it is properly configured and terminated. +Run CHKDSK /F to check for hard drive corruption, and then +restart your computer. . @@ -960,7 +1047,14 @@ Severity=Success Facility=System SymbolicName=UNEXPECTED_KERNEL_MODE_TRAP Language=English -UNEXPECTED_KERNEL_MODE_TRAP +Run a system diagnostic utility supplied by your hardware manufacturer. +In particular, run a memory check, and check for faulty or mismatched +memory. Try changing video adapters. + +Disable or remove any newly installed hardware and drivers. Disable or +remove any newly installed software. If you need to use Safe Mode to +remove or disable components, restart your computer, press F8 to select +Advanced Startup Options, and then select Safe Mode. . MessageId=0x7F @@ -974,6 +1068,14 @@ Hardware malfunction MessageId=0x80 Severity=Success Facility=System +SymbolicName=KERNEL_MODE_EXCEPTION_NOT_HANDLED +Language=English +KERNEL_MODE_EXCEPTION_NOT_HANDLED +. + +MessageId=0x8E +Severity=Success +Facility=System SymbolicName=SPIN_LOCK_INIT_FAILURE Language=English SPIN_LOCK_INIT_FAILURE @@ -995,6 +1097,22 @@ Language=English INVALID_WORK_QUEUE_ITEM . +MessageId=0xA5 +Severity=Success +Facility=System +SymbolicName=ACPI_BIOS_ERROR +Language=English +The BIOS in this system is not fully ACPI compliant. Please contact your +system vendor for an updated BIOS. +. + +MessageId=0xBE +Severity=Success +Facility=System +SymbolicName=ATTEMPTED_WRITE_TO_READONLY_MEMORY +Language=English +ATTEMPTED_WRITE_TO_READONLY_MEMORY + MessageId=0xC2 Severity=Success Facility=System @@ -1003,6 +1121,110 @@ Language=English BAD_POOL_CALLER . +MessageId=0xC3 +Severity=Success +Facility=System +SymbolicName=BUGCODE_PSS_MESSAGE_SIGNATURE +Language=English +A system file that is owned by ReactOS was replaced by an application +running on your system. The operating system detected this and tried to +verify the validity of the file's signature. The operating system found that +the file signature is not valid and put the original, correct file back +so that your operating system will continue to function properly. +. + +MessageId=0xC5 +Severity=Success +Facility=System +SymbolicName=DRIVER_CORRUPTED_EXPOOL +Language=English +A device driver has pool. + +Check to make sure any new hardware or software is properly installed. +If this is a new installation, ask your hardware or software manufacturer +for any ReactOS updates you might need. + +Run the driver verifier against any new (or suspect) drivers. +If that doesn't reveal the corrupting driver, try enabling special pool. +Both of these features are intended to catch the corruption at an earlier +point where the offending driver can be identified. + +If you need to use Safe Mode to remove or disable components, +restart your computer, press F8 to select Advanced Startup Options, +and then select Safe Mode. +. + +MessageId=0xCB +Severity=Success +Facility=System +SymbolicName=DRIVER_LEFT_LOCKED_PAGES_IN_PROCESS +Language=English +DRIVER_LEFT_LOCKED_PAGES_IN_PROCESS +. + +MessageId=0xCE +Severity=Success +Facility=System +SymbolicName=DRIVER_UNLOADED_WITHOUT_CANCELLING_PENDING_OPERATIONS +Language=English +DRIVER_UNLOADED_WITHOUT_CANCELLING_PENDING_OPERATIONS +. + +MessageId=0xD0 +Severity=Success +Facility=System +SymbolicName=DRIVER_CORRUPTED_MMPOOL +Language=English +DRIVER_CORRUPTED_MMPOOL +. + +MessageId=0xD1 +Severity=Success +Facility=System +SymbolicName=DRIVER_IRQL_NOT_LESS_OR_EQUAL +Language=English +DRIVER_IRQL_NOT_LESS_OR_EQUAL +. + +MessageId=0xD3 +Severity=Success +Facility=System +SymbolicName=DRIVER_PORTION_MUST_BE_NONPAGED +Language=English +DRIVER_PORTION_MUST_BE_NONPAGED +. + +MessageId=0xD8 +Severity=Success +Facility=System +SymbolicName=DRIVER_USED_EXCESSIVE_PTES +Language=English +DRIVER_USED_EXCESSIVE_PTES +. + +MessageId=0xD4 +Severity=Success +Facility=System +SymbolicName=SYSTEM_SCAN_AT_RAISED_IRQL_CAUGHT_IMPROPER_DRIVER_UNLOAD +Language=English +SYSTEM_SCAN_AT_RAISED_IRQL_CAUGHT_IMPROPER_DRIVER_UNLOAD +. + +MessageId=0xE0 +Severity=Success +Facility=System +SymbolicName=ACPI_BIOS_FATAL_ERROR +Language=English + +Your computer (BIOS) has reported that a component in your system is faulty and +has prevented ReactOS from operating. You can determine which component is +faulty by running the diagnostic disk or tool that came with your computer. + +If you do not have this tool, you must contact your system vendor and report +this error message to them. They will be able to assist you in correcting this +hardware problem thereby allowing ReactOS to operate. +. + MessageId=0xE1 Severity=Success Facility=System @@ -1035,6 +1257,14 @@ Language=English WORKER_INVALID . +MessageId=0xE5 +Severity=Success +Facility=System +SymbolicName=POWER_FAILURE_SIMULATE +Language=English +POWER_FAILURE_SIMULATE +. + MessageId=0xFA Severity=Success Facility=System @@ -1101,6 +1331,19 @@ Language=English ACTIVE_EX_WORKER_THREAD_TERMINATION . +MessageId=0xEA +Severity=Success +Facility=System +SymbolicName=THREAD_STUCK_IN_DEVICE_DRIVER +Language=English + +The device driver got stuck in an infinite loop. This usually indicates +problem with the device itself or with the device driver programming the +hardware incorrectly. + +Please check with your hardware device vendor for any driver updates. +. + MessageId=0xEF Severity=Success Facility=System