diff --git a/reactos/dll/ntdll/def/ntdll.pspec b/reactos/dll/ntdll/def/ntdll.pspec index d1ae0cbd155..7eb3e5519e9 100644 --- a/reactos/dll/ntdll/def/ntdll.pspec +++ b/reactos/dll/ntdll/def/ntdll.pspec @@ -895,7 +895,7 @@ @ stdcall RtlSetSecurityObject(long ptr ptr ptr ptr) //@ stdcall RtlSetSecurityObjectEx //@ stdcall RtlSetThreadErrorMode -//@ stdcall RtlSetThreadIsCritical +@ stdcall RtlSetThreadIsCritical(long ptr long) //@ stdcall RtlSetThreadPoolStartFunc @ stdcall RtlSetTimeZoneInformation(ptr) //@ stdcall RtlSetTimer diff --git a/reactos/dll/ntdll/def/ntdll.spec b/reactos/dll/ntdll/def/ntdll.spec index d1026472f2d..ec779e88411 100644 --- a/reactos/dll/ntdll/def/ntdll.spec +++ b/reactos/dll/ntdll/def/ntdll.spec @@ -895,7 +895,7 @@ @ stdcall RtlSetSecurityObject(long ptr ptr ptr ptr) ;@ stdcall RtlSetSecurityObjectEx ;@ stdcall RtlSetThreadErrorMode -;@ stdcall RtlSetThreadIsCritical +@ stdcall RtlSetThreadIsCritical(long ptr long) ;@ stdcall RtlSetThreadPoolStartFunc @ stdcall RtlSetTimeZoneInformation(ptr) ;@ stdcall RtlSetTimer diff --git a/reactos/include/ndk/rtlfuncs.h b/reactos/include/ndk/rtlfuncs.h index 50b2a0bd3b3..081027cc763 100644 --- a/reactos/include/ndk/rtlfuncs.h +++ b/reactos/include/ndk/rtlfuncs.h @@ -2406,6 +2406,15 @@ RtlSetProcessIsCritical( IN BOOLEAN NeedBreaks ); +NTSYSAPI +NTSTATUS +NTAPI +RtlSetThreadIsCritical( + IN BOOLEAN NewValue, + OUT PBOOLEAN OldValue OPTIONAL, + IN BOOLEAN NeedBreaks +); + NTSYSAPI ULONG NTAPI diff --git a/reactos/include/reactos/subsys/sm/smmsg.h b/reactos/include/reactos/subsys/sm/smmsg.h index 5c30ff24cc3..cf60d8871bc 100644 --- a/reactos/include/reactos/subsys/sm/smmsg.h +++ b/reactos/include/reactos/subsys/sm/smmsg.h @@ -53,6 +53,7 @@ typedef struct _SM_EXEC_PGM_MSG RTL_USER_PROCESS_INFORMATION ProcessInformation; BOOLEAN DebugFlag; } SM_EXEC_PGM_MSG, *PM_EXEC_PGM_MSG; +C_ASSERT(sizeof(SM_EXEC_PGM_MSG) == 0x48); typedef struct _SM_LOAD_DEFERED_SUBSYSTEM_MSG { diff --git a/reactos/lib/rtl/process.c b/reactos/lib/rtl/process.c index ae91e2423f7..1a23086d16d 100644 --- a/reactos/lib/rtl/process.c +++ b/reactos/lib/rtl/process.c @@ -362,16 +362,19 @@ RtlSetProcessIsCritical(IN BOOLEAN NewValue, OUT PBOOLEAN OldValue OPTIONAL, IN BOOLEAN NeedBreaks) { - ULONG BreakOnTermination = FALSE; + ULONG BreakOnTermination; - if (OldValue) - *OldValue = FALSE; + /* Initialize to FALSE */ + if (OldValue) *OldValue = FALSE; /* Fail, if the critical breaks flag is required but is not set */ - if (NeedBreaks == TRUE && + if ((NeedBreaks) && !(NtCurrentPeb()->NtGlobalFlag & FLG_ENABLE_SYSTEM_CRIT_BREAKS)) + { return STATUS_UNSUCCESSFUL; + } + /* Check if the caller wants the old value */ if (OldValue) { /* Query and return the old break on termination flag for the process */ diff --git a/reactos/lib/rtl/thread.c b/reactos/lib/rtl/thread.c index 3213b338e64..717cdb2e45c 100644 --- a/reactos/lib/rtl/thread.c +++ b/reactos/lib/rtl/thread.c @@ -150,6 +150,48 @@ RtlpFreeUserStack(IN HANDLE Process, /* FUNCTIONS ***************************************************************/ + +/* + * @implemented + */ +NTSTATUS +NTAPI +RtlSetThreadIsCritical(IN BOOLEAN NewValue, + OUT PBOOLEAN OldValue OPTIONAL, + IN BOOLEAN NeedBreaks) +{ + ULONG BreakOnTermination; + + /* Initialize to FALSE */ + if (OldValue) *OldValue = FALSE; + + /* Fail, if the critical breaks flag is required but is not set */ + if ((NeedBreaks) && + !(NtCurrentPeb()->NtGlobalFlag & FLG_ENABLE_SYSTEM_CRIT_BREAKS)) + { + return STATUS_UNSUCCESSFUL; + } + + /* Check if the caller wants the old value */ + if (OldValue) + { + /* Query and return the old break on termination flag for the process */ + ZwQueryInformationThread(NtCurrentThread(), + ThreadBreakOnTermination, + &BreakOnTermination, + sizeof(ULONG), + NULL); + *OldValue = (BOOLEAN)BreakOnTermination; + } + + /* Set the break on termination flag for the process */ + BreakOnTermination = NewValue; + return ZwSetInformationThread(NtCurrentThread(), + ThreadBreakOnTermination, + &BreakOnTermination, + sizeof(ULONG)); +} + /* @implemented */