xbox-kernel/private/ntos/ps/psspnd.c
2020-09-30 17:17:25 +02:00

163 lines
3.2 KiB
C

/*++
Copyright (c) 1989 Microsoft Corporation
Module Name:
psspnd.c
Abstract:
This module implements NtSuspendThread and NtResumeThread
Author:
Mark Lucovsky (markl) 25-May-1989
Revision History:
--*/
#include "psp.h"
NTSTATUS
NtSuspendThread(
IN HANDLE ThreadHandle,
OUT PULONG PreviousSuspendCount OPTIONAL
)
/*++
Routine Description:
This function suspends the target thread, and optionally
returns the previous suspend count.
Arguments:
ThreadHandle - Supplies a handle to the thread object to suspend.
PreviousSuspendCount - An optional parameter, that if specified
points to a variable that receives the thread's previous suspend
count.
Return Value:
Status of operation.
--*/
{
PETHREAD Thread;
NTSTATUS st;
ULONG LocalPreviousSuspendCount;
PAGED_CODE();
st = ObReferenceObjectByHandle(
ThreadHandle,
&PsThreadObjectType,
(PVOID *)&Thread
);
if ( !NT_SUCCESS(st) ) {
return st;
}
try {
if ( Thread != PsGetCurrentThread() ) {
if ( Thread->Tcb.HasTerminated ) {
ObDereferenceObject(Thread);
return STATUS_THREAD_IS_TERMINATING;
}
LocalPreviousSuspendCount = (ULONG) KeSuspendThread(&Thread->Tcb);
} else {
LocalPreviousSuspendCount = (ULONG) KeSuspendThread(&Thread->Tcb);
}
ObDereferenceObject(Thread);
if (ARGUMENT_PRESENT(PreviousSuspendCount))
*PreviousSuspendCount = LocalPreviousSuspendCount;
} except (EXCEPTION_EXECUTE_HANDLER) {
st = GetExceptionCode();
//
// Either the suspend, or the store could cause an
// exception. The store is a partial success, while the
// suspend exception is an error
//
if ( st == STATUS_SUSPEND_COUNT_EXCEEDED ) {
ObDereferenceObject(Thread);
} else {
st = STATUS_SUCCESS;
}
return st;
}
return STATUS_SUCCESS;
}
NTSTATUS
NtResumeThread(
IN HANDLE ThreadHandle,
OUT PULONG PreviousSuspendCount OPTIONAL
)
/*++
Routine Description:
This function resumes the target thread, and optionally
returns the previous suspend count.
Arguments:
ThreadHandle - Supplies a handle to the thread object to resume.
PreviousSuspendCount - An optional parameter, that if specified
points to a variable that receives the thread's previous suspend
count.
Return Value:
Status of operation.
--*/
{
PETHREAD Thread;
NTSTATUS st;
ULONG LocalPreviousSuspendCount;
PAGED_CODE();
st = ObReferenceObjectByHandle(
ThreadHandle,
&PsThreadObjectType,
(PVOID *)&Thread
);
if ( !NT_SUCCESS(st) ) {
return st;
}
LocalPreviousSuspendCount = (ULONG) KeResumeThread(&Thread->Tcb);
ObDereferenceObject(Thread);
if (ARGUMENT_PRESENT(PreviousSuspendCount)) {
*PreviousSuspendCount = LocalPreviousSuspendCount;
}
return STATUS_SUCCESS;
}