📄 process.c
字号:
CsrImpersonateClient(CsrThread);
Status = CsrGetProcessLuid(NULL, &ProcessLuid);
CsrRevertToSelf();
}
}
if (!NT_SUCCESS(Status))
{
/* We didn't have access, so skip it */
CsrProcess->Flags |= CsrProcessSkipShutdown;
continue;
}
/* Check if this is the System LUID */
if ((IsSystemLuid = RtlEqualLuid(&ProcessLuid, &SystemLuid)))
{
/* Mark this process */
CsrProcess->ShutdownFlags |= CsrShutdownSystem;
}
else if (!(IsOurLuid = RtlEqualLuid(&ProcessLuid, CallerLuid)))
{
/* Our LUID doesn't match with the caller's */
CsrProcess->ShutdownFlags |= CsrShutdownOther;
}
/* Check if we're past the previous level */
if (CsrProcess->ShutdownLevel > Level)
{
/* Update the level */
Level = CsrProcess->ShutdownLevel;
/* Set the final process */
ReturnCsrProcess = CsrProcess;
}
}
/* Check if we found a process */
if (ReturnCsrProcess)
{
/* Skip this one next time */
ReturnCsrProcess->Flags |= CsrProcessSkipShutdown;
}
return ReturnCsrProcess;
}
/* PUBLIC FUNCTIONS ***********************************************************/
/*++
* @name CsrCreateProcess
* @implemented NT4
*
* Do nothing for 500ms.
*
* @param ArgumentCount
* Description of the parameter. Wrapped to more lines on ~70th
* column.
*
* @param Arguments
* Description of the parameter. Wrapped to more lines on ~70th
* column.
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
*
* @remarks None.
*
*--*/
NTSTATUS
NTAPI
CsrCreateProcess(IN HANDLE hProcess,
IN HANDLE hThread,
IN PCLIENT_ID ClientId,
IN PCSR_NT_SESSION NtSession,
IN ULONG Flags,
IN PCLIENT_ID DebugCid)
{
PCSR_THREAD CurrentThread = NtCurrentTeb()->CsrClientThread;
CLIENT_ID CurrentCid;
PCSR_PROCESS CurrentProcess;
PVOID ProcessData;
ULONG i;
PCSR_PROCESS CsrProcess;
NTSTATUS Status;
PCSR_THREAD CsrThread;
KERNEL_USER_TIMES KernelTimes;
/* Get the current CID and lock Processes */
CurrentCid = CurrentThread->ClientId;
CsrAcquireProcessLock();
/* Get the current CSR Thread */
CurrentThread = CsrLocateThreadByClientId(&CurrentProcess, &CurrentCid);
if (!CurrentThread)
{
/* We've failed to locate the thread */
CsrReleaseProcessLock();
return STATUS_THREAD_IS_TERMINATING;
}
/* Allocate a new Process Object */
if (!(CsrProcess = CsrAllocateProcess()))
{
/* Couldn't allocate Process */
CsrReleaseProcessLock();
return STATUS_NO_MEMORY;
}
/* Setup Process Data */
CsrProcess->ClientId = *ClientId;
CsrProcess->ProcessHandle = hProcess;
CsrProcess->ShutdownLevel = 0x280;
/* Inherit the Process Data */
ProcessData = &CurrentProcess->ServerData[CSR_SERVER_DLL_MAX];
for (i = 0; i < CSR_SERVER_DLL_MAX; i++)
{
/* Check if the DLL is Loaded and has Per Process Data */
if (CsrLoadedServerDll[i] && CsrLoadedServerDll[i]->SizeOfProcessData)
{
/* Set the pointer */
CsrProcess->ServerData[i] = ProcessData;
/* Copy the Data */
RtlMoveMemory(ProcessData,
CurrentProcess->ServerData[i],
CsrLoadedServerDll[i]->SizeOfProcessData);
/* Update next data pointer */
ProcessData = (PVOID)((ULONG_PTR)ProcessData +
CsrLoadedServerDll[i]->SizeOfProcessData);
}
else
{
/* No data for this Server */
CsrProcess->ServerData[i] = NULL;
}
}
/* Set the Exception port to us */
Status = NtSetInformationProcess(hProcess,
ProcessExceptionPort,
&CsrApiPort,
sizeof(HANDLE));
if (!NT_SUCCESS(Status))
{
/* Failed */
CsrDeallocateProcess(CsrProcess);
CsrReleaseProcessLock();
return STATUS_NO_MEMORY;
}
/* If Check if CreateProcess got CREATE_NEW_PROCESS_GROUP */
if (!(Flags & CsrProcessCreateNewGroup))
{
/* Create new data */
CsrProcess->ProcessGroupId = HandleToUlong(ClientId->UniqueProcess);
CsrProcess->ProcessGroupSequence = CsrProcess->SequenceNumber;
}
else
{
/* Copy it from the current process */
CsrProcess->ProcessGroupId = CurrentProcess->ProcessGroupId;
CsrProcess->ProcessGroupSequence = CurrentProcess->ProcessGroupSequence;
}
/* Check if this is a console process */
if(Flags & CsrProcessIsConsoleApp) CsrProcess->Flags |= CsrProcessIsConsoleApp;
/* Mask out non-debug flags */
Flags &= ~(CsrProcessIsConsoleApp | CsrProcessCreateNewGroup);
/* Check if every process will be debugged */
if (!Flags && CurrentProcess->DebugFlags & CsrDebugProcessChildren)
{
/* Pass it on to the current process */
CsrProcess->DebugFlags = CsrDebugProcessChildren;
CsrProcess->DebugCid = CurrentProcess->DebugCid;
}
/* Check if Debugging was used on this process */
if (Flags & (CsrDebugOnlyThisProcess | CsrDebugProcessChildren))
{
/* Save the debug flag used */
CsrProcess->DebugFlags = Flags;
/* Save the CID */
if (DebugCid) CsrProcess->DebugCid = *DebugCid;
}
/* Check if we debugging is enabled */
if (CsrProcess->DebugFlags)
{
/* Set the Debug Port to us */
Status = NtSetInformationProcess(hProcess,
ProcessDebugPort,
&CsrApiPort,
sizeof(HANDLE));
if (!NT_SUCCESS(Status))
{
/* Failed */
CsrDeallocateProcess(CsrProcess);
CsrReleaseProcessLock();
return STATUS_NO_MEMORY;
}
}
/* Get the Thread Create Time */
Status = NtQueryInformationThread(hThread,
ThreadTimes,
(PVOID)&KernelTimes,
sizeof(KernelTimes),
NULL);
/* Allocate a CSR Thread Structure */
CsrThread = CsrAllocateThread(CsrProcess);
if (CsrThread == NULL)
{
/* Failed */
CsrDeallocateProcess(CsrProcess);
CsrReleaseProcessLock();
return STATUS_NO_MEMORY;
}
/* Save the data we have */
CsrThread->CreateTime = KernelTimes.CreateTime;
CsrThread->ClientId = *ClientId;
CsrThread->ThreadHandle = hThread;
CsrThread->Flags = 0;
/* Insert the Thread into the Process */
CsrInsertThread(CsrProcess, CsrThread);
/* Reference the session */
CsrReferenceNtSession(NtSession);
CsrProcess->NtSession = NtSession;
/* Set the Priority to Background */
CsrSetBackgroundPriority(CsrProcess);
/* Insert the Process */
CsrInsertProcess(NULL, CurrentProcess, CsrProcess);
/* Release lock and return */
CsrReleaseProcessLock();
return Status;
}
/*++
* @name CsrDebugProcess
* @implemented NT4
*
* The CsrDebugProcess routine is deprecated in NT 5.1 and higher. It is
* exported only for compatibility with older CSR Server DLLs.
*
* @param CsrProcess
* Deprecated.
*
* @return Deprecated
*
* @remarks Deprecated.
*
*--*/
NTSTATUS
NTAPI
CsrDebugProcess(PCSR_PROCESS CsrProcess)
{
/* CSR does not handle debugging anymore */
DPRINT("CSRSRV: %s(%08lx) called\n", __FUNCTION__, CsrProcess);
return STATUS_UNSUCCESSFUL;
}
/*++
* @name CsrServerInitialization
* @implemented NT4
*
* The CsrDebugProcessStop routine is deprecated in NT 5.1 and higher. It is
* exported only for compatibility with older CSR Server DLLs.
*
* @param CsrProcess
* Deprecated.
*
* @return Deprecated
*
* @remarks Deprecated.
*
*--*/
NTSTATUS
NTAPI
CsrDebugProcessStop(PCSR_PROCESS CsrProcess)
{
/* CSR does not handle debugging anymore */
DPRINT("CSRSRV: %s(%08lx) called\n", __FUNCTION__, CsrProcess);
return STATUS_UNSUCCESSFUL;
}
/*++
* @name CsrDereferenceProcess
* @implemented NT4
*
* The CsrDereferenceProcess routine removes a reference from a CSR Process.
*
* @param CsrThread
* Pointer to the CSR Process to dereference.
*
* @return None.
*
* @remarks If the reference count has reached zero (ie: the CSR Process has
* no more active references), it will be deleted.
*
*--*/
VOID
NTAPI
CsrDereferenceProcess(PCSR_PROCESS CsrProcess)
{
/* Acquire process lock */
CsrAcquireProcessLock();
/* Decrease reference count */
if (!(--CsrProcess->ReferenceCount))
{
/* Call the generic cleanup code */
CsrProcessRefcountZero(CsrProcess);
}
else
{
/* Just release the lock */
CsrReleaseProcessLock();
}
}
/*++
* @name CsrDestroyProcess
* @implemented NT4
*
* The CsrDestroyProcess routine destroys the CSR Process corresponding to
* a given Client ID.
*
* @param Cid
* Pointer to the Client ID Structure corresponding to the CSR
* Process which is about to be destroyed.
*
* @param ExitStatus
* Unused.
*
* @return STATUS_SUCCESS in case of success, STATUS_THREAD_IS_TERMINATING
* if the CSR Process is already terminating.
*
* @remarks None.
*
*--*/
NTSTATUS
NTAPI
CsrDestroyProcess(IN PCLIENT_ID Cid,
IN NTSTATUS ExitStatus)
{
PCSR_THREAD CsrThread;
PCSR_PROCESS CsrProcess;
CLIENT_ID ClientId = *Cid;
PLIST_ENTRY ListHead, NextEntry;
/* Acquire lock */
CsrAcquireProcessLock();
/* Find the thread */
CsrThread = CsrLocateThreadByClientId(&CsrProcess,
&ClientId);
/* Make sure we got one back, and that it's not already gone */
if (!CsrThread || CsrProcess->Flags & CsrProcessTerminating)
{
/* Release the lock and return failure */
CsrReleaseProcessLock();
return STATUS_THREAD_IS_TERMINATING;
}
/* Set the terminated flag */
CsrProcess->Flags |= CsrProcessTerminating;
/* Get the List Pointers */
ListHead = &CsrProcess->ThreadList;
NextEntry = ListHead->Flink;
/* Loop the list */
while (NextEntry != ListHead)
{
/* Get the current thread entry */
CsrThread = CONTAINING_RECORD(NextEntry, CSR_THREAD, Link);
/* Move to the next entry */
NextEntry = NextEntry->Flink;
/* Make sure the thread isn't already dead */
if (CsrThread->Flags & CsrThreadTerminated) continue;
/* Set the Terminated flag */
CsrThread->Flags |= CsrThreadTerminated;
/* Acquire the Wait Lock */
CsrAcquireWaitLock();
/* Do we have an active wait block? */
if (CsrThread->WaitBlock)
{
/* Notify waiters of termination */
CsrNotifyWaitBlock(CsrThread->WaitBlock,
NULL,
NULL,
NULL,
CsrProcessTerminating,
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -