diff --git a/reactos/ntoskrnl/ex/error.c b/reactos/ntoskrnl/ex/error.c index 23cd803ae5f..33c2131ab1b 100644 --- a/reactos/ntoskrnl/ex/error.c +++ b/reactos/ntoskrnl/ex/error.c @@ -112,11 +112,6 @@ ExpRaiseHardError(IN NTSTATUS ErrorStatus, HANDLE PortHandle; KPROCESSOR_MODE PreviousMode = KeGetPreviousMode(); PAGED_CODE(); - DPRINT1("Hard error, baby!: %lx, %lx, %lx %p\n", - ErrorStatus, - NumberOfParameters, - UnicodeStringParameterMask, - Parameters); /* Check if this error will shutdown the system */ if (ValidResponseOptions == OptionShutdownSystem) @@ -235,15 +230,42 @@ ExpRaiseHardError(IN NTSTATUS ErrorStatus, Parameters, sizeof(ULONG_PTR) * NumberOfParameters); - /* Send the message */ + /* Send the LPC Message */ Status = LpcRequestWaitReplyPort(PortHandle, (PVOID)Message, (PVOID)Message); - DPRINT1("Checkpoint 2: %lx\n", Status); + if (NT_SUCCESS(Status)) + { + /* Check what kind of response we got */ + if ((Message->Response != ResponseReturnToCaller) && + (Message->Response != ResponseNotHandled) && + (Message->Response != ResponseAbort) && + (Message->Response != ResponseCancel) && + (Message->Response != ResponseIgnore) && + (Message->Response != ResponseNo) && + (Message->Response != ResponseOk) && + (Message->Response != ResponseRetry) && + (Message->Response != ResponseYes) && + (Message->Response != ResponseTryAgain) && + (Message->Response != ResponseContinue)) + { + /* Reset to a default one */ + Message->Response = ResponseReturnToCaller; + } + + /* Set the response */ + *Response = Message->Response; + } + } + else + { + /* Set defaults */ + *Response = ResponseReturnToCaller; + Status = STATUS_SUCCESS; } - UNIMPLEMENTED; - return STATUS_NOT_IMPLEMENTED; + /* Return status */ + return Status; } /*++ diff --git a/reactos/ntoskrnl/lpc/reply.c b/reactos/ntoskrnl/lpc/reply.c index 58159f885d0..5fb58c22fb6 100644 --- a/reactos/ntoskrnl/lpc/reply.c +++ b/reactos/ntoskrnl/lpc/reply.c @@ -429,22 +429,26 @@ LpcRequestWaitReplyPort(IN PVOID Port, { HANDLE PortHandle; NTSTATUS Status; + UNICODE_STRING PortName; + ULONG ConnectInfoLength; - /* This is a SICK hack */ - Status = ObOpenObjectByPointer(Port, - 0, - NULL, - PORT_ALL_ACCESS, - LpcPortObjectType, - KernelMode, - &PortHandle); - DPRINT1("LPC Hack active: %lx %lx\n", Status, PortHandle); + // + // OMG HAXX! + // + RtlInitUnicodeString(&PortName, L"\\Windows\\ApiPort"); + ConnectInfoLength = 0; + Status = ZwConnectPort(&PortHandle, + &PortName, + NULL, + NULL, + NULL, + NULL, + NULL, + &ConnectInfoLength); - /* Call the Nt function. Do a ring transition to get Kmode. */ Status = ZwRequestWaitReplyPort(PortHandle, LpcMessageRequest, LpcMessageReply); - DPRINT1("LPC Hack active: %lx %lx\n", Status, PortHandle); /* Close the handle */ ObCloseHandle(PortHandle, KernelMode); diff --git a/reactos/ntoskrnl/lpc/send.c b/reactos/ntoskrnl/lpc/send.c index 53bae7280c8..1dc522f7e66 100644 --- a/reactos/ntoskrnl/lpc/send.c +++ b/reactos/ntoskrnl/lpc/send.c @@ -288,7 +288,7 @@ NtRequestWaitReplyPort (IN HANDLE PortHandle, Status = EiReplyOrRequestPort(Port->OtherPort, LpcRequest, - LPC_REQUEST, + LpcRequest->u2.s2.Type == LPC_ERROR_EVENT ? LPC_ERROR_EVENT : LPC_REQUEST, Port); if (!NT_SUCCESS(Status)) { diff --git a/reactos/subsystems/win32/csrss/api/wapi.c b/reactos/subsystems/win32/csrss/api/wapi.c index 92a726e416a..c647a052f5a 100644 --- a/reactos/subsystems/win32/csrss/api/wapi.c +++ b/reactos/subsystems/win32/csrss/api/wapi.c @@ -104,6 +104,20 @@ CsrApiCallHandler(PCSRSS_PROCESS_DATA ProcessData, } } +BOOL FASTCALL CallHardError(void); + +static +VOID +NTAPI +CsrHandleHardError(IN PCSRSS_PROCESS_DATA ProcessData, + IN OUT PHARDERROR_MSG Message) +{ + DPRINT1("CSR: received hard error %lx\n", Message->Status); + + /* Call the hard error handler in win32csr */ + CallHardError(); +} + static VOID STDCALL @@ -133,7 +147,7 @@ ClientConnectionThread(HANDLE ServerPort) DPRINT1("NtReplyWaitReceivePort failed\n"); break; } - + /* If the connection was closed, handle that */ if (Request->Header.u2.s2.Type == LPC_PORT_CLOSED) { @@ -161,9 +175,18 @@ ClientConnectionThread(HANDLE ServerPort) continue; } - /* Call the Handler */ - CsrApiCallHandler(ProcessData, Request); - + /* Check if we got a hard error */ + if (Request->Header.u2.s2.Type == LPC_ERROR_EVENT) + { + /* Call the Handler */ + CsrHandleHardError(ProcessData, (PHARDERROR_MSG)Request); + } + else + { + /* Call the Handler */ + CsrApiCallHandler(ProcessData, Request); + } + /* Send back the reply */ Reply = Request; } diff --git a/reactos/subsystems/win32/csrss/include/csrplugin.h b/reactos/subsystems/win32/csrss/include/csrplugin.h index 9a435cbc086..a5f250b2c1a 100644 --- a/reactos/subsystems/win32/csrss/include/csrplugin.h +++ b/reactos/subsystems/win32/csrss/include/csrplugin.h @@ -43,9 +43,12 @@ typedef struct tagCSRSS_EXPORTED_FUNCS typedef BOOL (STDCALL *CSRPLUGIN_INIT_COMPLETE_PROC)(void); +typedef BOOL (STDCALL *CSRPLUGIN_HARDERROR_PROC)(void); + typedef BOOL (STDCALL *CSRPLUGIN_INITIALIZE_PROC)(PCSRSS_API_DEFINITION *ApiDefinitions, PCSRSS_OBJECT_DEFINITION *ObjectDefinitions, CSRPLUGIN_INIT_COMPLETE_PROC *InitCompleteProc, + CSRPLUGIN_HARDERROR_PROC *HardErrorProc, PCSRSS_EXPORTED_FUNCS Exports, HANDLE CsrssApiHeap); diff --git a/reactos/subsystems/win32/csrss/init.c b/reactos/subsystems/win32/csrss/init.c index d1b80bc461f..9ff6bf5e999 100644 --- a/reactos/subsystems/win32/csrss/init.c +++ b/reactos/subsystems/win32/csrss/init.c @@ -28,6 +28,9 @@ extern HANDLE CsrssApiHeap; static unsigned InitCompleteProcCount; static CSRPLUGIN_INIT_COMPLETE_PROC *InitCompleteProcs = NULL; +static unsigned HardErrorProcCount; +static CSRPLUGIN_HARDERROR_PROC *HardErrorProcs = NULL; + HANDLE hSbApiPort = (HANDLE) 0; HANDLE hBootstrapOk = (HANDLE) 0; @@ -66,6 +69,34 @@ CsrpAddInitCompleteProc(CSRPLUGIN_INIT_COMPLETE_PROC Proc) return STATUS_SUCCESS; } +static NTSTATUS FASTCALL +CsrpAddHardErrorProc(CSRPLUGIN_HARDERROR_PROC Proc) +{ + CSRPLUGIN_HARDERROR_PROC *NewProcs; + + DPRINT("CSR: %s called\n", __FUNCTION__); + + NewProcs = RtlAllocateHeap(CsrssApiHeap, 0, + (HardErrorProcCount + 1) + * sizeof(CSRPLUGIN_HARDERROR_PROC)); + if (NULL == NewProcs) + { + return STATUS_NO_MEMORY; + } + if (0 != HardErrorProcCount) + { + RtlCopyMemory(NewProcs, HardErrorProcs, + HardErrorProcCount * sizeof(CSRPLUGIN_HARDERROR_PROC)); + RtlFreeHeap(CsrssApiHeap, 0, HardErrorProcs); + } + + NewProcs[HardErrorProcCount] = Proc; + HardErrorProcs = NewProcs; + HardErrorProcCount++; + + return STATUS_SUCCESS; +} + /********************************************************************** * CallInitComplete/0 */ @@ -90,6 +121,27 @@ CallInitComplete(void) return Ok; } +BOOL +FASTCALL +CallHardError(void) +{ + BOOL Ok; + unsigned i; + + DPRINT("CSR: %s called\n", __FUNCTION__); + + Ok = TRUE; + if (0 != HardErrorProcCount) + { + for (i = 0; i < HardErrorProcCount && Ok; i++) + { + Ok = (*(HardErrorProcs[i]))(); + } + } + + return Ok; +} + ULONG InitializeVideoAddressSpace(VOID); @@ -182,6 +234,7 @@ CsrpInitWin32Csr (int argc, char ** argv, char ** envp) PCSRSS_API_DEFINITION ApiDefinitions; PCSRSS_OBJECT_DEFINITION ObjectDefinitions; CSRPLUGIN_INIT_COMPLETE_PROC InitCompleteProc; + CSRPLUGIN_HARDERROR_PROC HardErrorProc; DPRINT("CSR: %s called\n", __FUNCTION__); @@ -202,7 +255,7 @@ CsrpInitWin32Csr (int argc, char ** argv, char ** envp) Exports.CsrReleaseObjectProc = CsrReleaseObject; Exports.CsrEnumProcessesProc = CsrEnumProcesses; if (! (*InitProc)(&ApiDefinitions, &ObjectDefinitions, &InitCompleteProc, - &Exports, CsrssApiHeap)) + &HardErrorProc, &Exports, CsrssApiHeap)) { return STATUS_UNSUCCESSFUL; } @@ -221,6 +274,7 @@ CsrpInitWin32Csr (int argc, char ** argv, char ** envp) { Status = CsrpAddInitCompleteProc(InitCompleteProc); } + if (HardErrorProc) Status = CsrpAddHardErrorProc(HardErrorProc); return Status; } diff --git a/reactos/subsystems/win32/csrss/win32csr/dllmain.c b/reactos/subsystems/win32/csrss/win32csr/dllmain.c index 683ec5172fc..31272065ca6 100644 --- a/reactos/subsystems/win32/csrss/win32csr/dllmain.c +++ b/reactos/subsystems/win32/csrss/win32csr/dllmain.c @@ -163,10 +163,19 @@ Win32CsrInitComplete(void) return TRUE; } +static BOOL STDCALL +Win32CsrHardError(void) +{ + MessageBox(0, "Hard Error", "TODO", 0); + return TRUE; +} + + BOOL STDCALL Win32CsrInitialization(PCSRSS_API_DEFINITION *ApiDefinitions, PCSRSS_OBJECT_DEFINITION *ObjectDefinitions, CSRPLUGIN_INIT_COMPLETE_PROC *InitComplete, + CSRPLUGIN_HARDERROR_PROC *HardError, PCSRSS_EXPORTED_FUNCS Exports, HANDLE CsrssApiHeap) { @@ -179,6 +188,7 @@ Win32CsrInitialization(PCSRSS_API_DEFINITION *ApiDefinitions, *ApiDefinitions = Win32CsrApiDefinitions; *ObjectDefinitions = Win32CsrObjectDefinitions; *InitComplete = Win32CsrInitComplete; + *HardError = Win32CsrHardError; return TRUE; } diff --git a/reactos/subsystems/win32/csrss/win32csr/win32csr.def b/reactos/subsystems/win32/csrss/win32csr/win32csr.def index a4ebf9faf26..9fa863db822 100644 --- a/reactos/subsystems/win32/csrss/win32csr/win32csr.def +++ b/reactos/subsystems/win32/csrss/win32csr/win32csr.def @@ -5,4 +5,4 @@ LIBRARY win32csr.dll EXPORTS -Win32CsrInitialization@20 +Win32CsrInitialization@24