[CSRSRV2/CSRSS2]: Make multiple fixes to, bring up to speed, and finish implementation of the CSRSS/CSRSRV that has been laying around in trunk since forever. Not yet tested if it actually works yet, but it should now build and be much closer to fully functional. Of course, the trick is to figure out how to get it to co-exist with the current CSRSS/win32csr.

svn path=/trunk/; revision=55585
This commit is contained in:
Alex Ionescu 2012-02-14 00:57:32 +00:00
parent 9e265ba699
commit b5303c046f
17 changed files with 1383 additions and 1207 deletions

View file

@ -18,7 +18,7 @@
typedef struct _CSR_NT_SESSION
{
ULONG ReferenceCount;
LIST_ENTRY SessionList;
LIST_ENTRY SessionLink;
ULONG SessionId;
} CSR_NT_SESSION, *PCSR_NT_SESSION;
@ -71,12 +71,21 @@ typedef enum _CSR_PROCESS_FLAGS
{
CsrProcessTerminating = 0x1,
CsrProcessSkipShutdown = 0x2,
CsrProcessNormalPriority = 0x10,
CsrProcessIdlePriority = 0x20,
CsrProcessHighPriority = 0x40,
CsrProcessRealtimePriority = 0x80,
CsrProcessCreateNewGroup = 0x100,
CsrProcessTerminated = 0x200,
CsrProcessLastThreadTerminated = 0x400,
CsrProcessIsConsoleApp = 0x800
} CSR_PROCESS_FLAGS, *PCSR_PROCESS_FLAGS;
#define CsrProcessPriorityFlags (CsrProcessNormalPriority | \
CsrProcessIdlePriority | \
CsrProcessHighPriority | \
CsrProcessRealtimePriority)
typedef enum _CSR_THREAD_FLAGS
{
CsrThreadAltertable = 0x1,
@ -252,75 +261,6 @@ typedef struct _CSR_WAIT_BLOCK
CSR_API_MESSAGE WaitApiMessage;
} CSR_WAIT_BLOCK, *PCSR_WAIT_BLOCK;
/* FIXME: Put into new SM headers */
typedef struct _SB_CREATE_SESSION
{
ULONG SessionId;
RTL_USER_PROCESS_INFORMATION ProcessInfo;
} SB_CREATE_SESSION, *PSB_CREATE_SESSION;
typedef struct _SB_TERMINATE_SESSION
{
ULONG SessionId;
} SB_TERMINATE_SESSION, *PSB_TERMINATE_SESSION;
typedef struct _SB_FOREIGN_SESSION_COMPLETE
{
ULONG SessionId;
} SB_FOREIGN_SESSION_COMPLETE, *PSB_FOREIGN_SESSION_COMPLETE;
typedef struct _SB_CREATE_PROCESS
{
ULONG SessionId;
} SB_CREATE_PROCESS, *PSB_CREATE_PROCESS;
typedef struct _SB_CONNECTION_INFO
{
ULONG SubsystemId;
} SB_CONNECTION_INFO, *PSB_CONNECTION_INFO;
typedef struct _SB_API_MESSAGE
{
PORT_MESSAGE Header;
union
{
SB_CONNECTION_INFO ConnectionInfo;
struct
{
ULONG Opcode;
NTSTATUS Status;
union
{
SB_CREATE_SESSION SbCreateSession;
SB_TERMINATE_SESSION SbTerminateSession;
SB_FOREIGN_SESSION_COMPLETE SbForeignSessionComplete;
SB_CREATE_PROCESS SbCreateProcess;
};
};
};
} SB_API_MESSAGE, *PSB_API_MESSAGE;
typedef
BOOLEAN
(NTAPI *PSB_API_ROUTINE)(IN PSB_API_MESSAGE ApiMessage);
NTSTATUS
NTAPI
SmSessionComplete(
IN HANDLE hApiPort,
IN ULONG SessionId,
IN NTSTATUS Status
);
NTSTATUS
NTAPI
SmConnectToSm(
IN PUNICODE_STRING SbApiPortName OPTIONAL,
IN HANDLE hSbApiPort OPTIONAL,
IN ULONG SubsystemType OPTIONAL,
OUT PHANDLE hSmApiPort
);
/* PROTOTYPES ****************************************************************/
NTSTATUS

View file

@ -1,4 +1,5 @@
if(ARCH MATCHES i386)
add_subdirectory(ntvdm)
endif()
add_subdirectory(csr)
add_subdirectory(win32)

View file

@ -0,0 +1,16 @@
include_directories(
include
${REACTOS_SOURCE_DIR}/include/reactos/subsys
${REACTOS_SOURCE_DIR}/include/reactos/drivers)
add_executable(csrss2 main.c csr.rc)
set_module_type(csrss2 nativecui)
target_link_libraries(csrss2 nt)
add_importlibs(csrss2 ntdll csrsrv2)
add_dependencies(csrss2 psdk bugcodes)
add_cd_file(TARGET csrss2 DESTINATION reactos/system32 FOR all)
add_subdirectory(csrsrv)

View file

@ -1,15 +0,0 @@
<?xml version="1.0"?>
<!DOCTYPE group SYSTEM "../../tools/rbuild/project.dtd">
<group>
<module name="csr" type="nativecui" installbase="system32" installname="csr.exe">
<include base="csr">.</include>
<include base="ReactOS">include/reactos/subsys</include>
<library>nt</library>
<library>ntdll</library>
<library>csrsrv</library>
<file>main.c</file>
</module>
<directory name="csrsrv">
<xi:include href="csrsrv/csrsrv.rbuild" />
</directory>
</group>

View file

@ -0,0 +1,30 @@
include_directories(${REACTOS_SOURCE_DIR}/subsystems/win32/csrss/include)
include_directories(${REACTOS_SOURCE_DIR}/include/reactos/subsys)
spec2def(csrsrv2.dll csrsrv2.spec)
list(APPEND SOURCE
api.c
init.c
process.c
server.c
session.c
thread.c
wait.c
csrsrv.rc
${CMAKE_CURRENT_BINARY_DIR}/csrsrv2.def)
add_library(csrsrv2 SHARED ${SOURCE})
target_link_libraries(csrsrv2 ${PSEH_LIB} smlib)
set_module_type(csrsrv2 nativedll)
add_importlibs(csrsrv2 ntdll)
add_pch(csrsrv2 srv.h)
add_dependencies(csrsrv2 psdk bugcodes)
add_cd_file(TARGET csrsrv2 DESTINATION reactos/system32 FOR all)
add_importlib_target(csrsrv2.spec)

File diff suppressed because it is too large Load diff

View file

@ -1,18 +0,0 @@
<?xml version="1.0"?>
<!DOCTYPE module SYSTEM "../../../tools/rbuild/project.dtd">
<module name="csrsrv" type="nativedll">
<importlibrary definition="csrsrv.spec" />
<include base="csrsrv">.</include>
<include base="csr">.</include>
<include base="ReactOS">include/reactos/subsys</include>
<library>ntdll</library>
<library>pseh</library>
<file>api.c</file>
<file>init.c</file>
<file>process.c</file>
<file>server.c</file>
<file>session.c</file>
<file>thread.c</file>
<file>wait.c</file>
<pch>srv.h</pch>
</module>

View file

@ -3,7 +3,7 @@
@ stdcall CsrConnectToUser()
@ stdcall CsrCreateProcess(ptr ptr ptr ptr long ptr)
@ stdcall CsrCreateRemoteThread(ptr ptr)
@ stdcall CsrCreateThread(ptr ptr ptr)
@ stdcall CsrCreateThread(ptr ptr ptr long)
@ stdcall CsrCreateWait(ptr ptr ptr ptr ptr ptr)
@ stdcall CsrDebugProcess(ptr)
@ stdcall CsrDebugProcessStop(ptr)

File diff suppressed because it is too large Load diff

View file

@ -22,6 +22,84 @@ ULONG CsrTotalPerProcessDataLength;
/* PRIVATE FUNCTIONS *********************************************************/
/*++
* @name ProtectHandle
* @implemented NT5.2
*
* The ProtectHandle routine protects an object handle against closure.
*
* @return TRUE or FALSE.
*
* @remarks None.
*
*--*/
BOOLEAN
NTAPI
ProtectHandle(IN HANDLE ObjectHandle)
{
NTSTATUS Status;
OBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo;
/* Query current state */
Status = NtQueryObject(ObjectHandle,
ObjectHandleFlagInformation,
&HandleInfo,
sizeof(HandleInfo),
NULL);
if (NT_SUCCESS(Status))
{
/* Enable protect from close */
HandleInfo.ProtectFromClose = TRUE;
Status = NtSetInformationObject(ObjectHandle,
ObjectHandleFlagInformation,
&HandleInfo,
sizeof(HandleInfo));
if (NT_SUCCESS(Status)) return TRUE;
}
/* We failed to or set the state */
return FALSE;
}
/*++
* @name UnProtectHandle
* @implemented NT5.2
*
* The UnProtectHandle routine unprotects an object handle against closure.
*
* @return TRUE or FALSE.
*
* @remarks None.
*
*--*/
BOOLEAN
NTAPI
UnProtectHandle(IN HANDLE ObjectHandle)
{
NTSTATUS Status;
OBJECT_HANDLE_ATTRIBUTE_INFORMATION HandleInfo;
/* Query current state */
Status = NtQueryObject(ObjectHandle,
ObjectHandleFlagInformation,
&HandleInfo,
sizeof(HandleInfo),
NULL);
if (NT_SUCCESS(Status))
{
/* Disable protect from close */
HandleInfo.ProtectFromClose = FALSE;
Status = NtSetInformationObject(ObjectHandle,
ObjectHandleFlagInformation,
&HandleInfo,
sizeof(HandleInfo));
if (NT_SUCCESS(Status)) return TRUE;
}
/* We failed to or set the state */
return FALSE;
}
/*++
* @name CsrAllocateProcess
* @implemented NT4
@ -49,8 +127,9 @@ CsrAllocateProcess(VOID)
CsrProcess = RtlAllocateHeap(CsrHeap, HEAP_ZERO_MEMORY, TotalSize);
if (!CsrProcess) return NULL;
/* Handle the Sequence Number */
/* Handle the Sequence Number and protect against overflow */
CsrProcess->SequenceNumber = CsrProcessSequenceCount++;
if (CsrProcessSequenceCount < 5) CsrProcessSequenceCount = 5;
/* Increase the reference count */
CsrProcess->ReferenceCount++;
@ -66,7 +145,7 @@ CsrAllocateProcess(VOID)
* @name CsrServerInitialization
* @implemented NT4
*
* The CsrInitializeProcesses routine sets up support for CSR Processes
* The CsrInitializeProcessStructure routine sets up support for CSR Processes
* and CSR Threads.
*
* @param None.
@ -79,13 +158,14 @@ CsrAllocateProcess(VOID)
*--*/
NTSTATUS
NTAPI
CsrInitializeProcesses(VOID)
CsrInitializeProcessStructure(VOID)
{
NTSTATUS Status;
ULONG i;
/* Initialize the Lock */
Status = RtlInitializeCriticalSection(&CsrProcessLock);
if (!NT_SUCCESS(Status)) return Status;
/* Set up the Root Process */
CsrRootProcess = CsrAllocateProcess();
@ -100,8 +180,7 @@ CsrInitializeProcesses(VOID)
for (i = 0; i < 256; i++) InitializeListHead(&CsrThreadHashTable[i]);
/* Initialize the Wait Lock */
Status = RtlInitializeCriticalSection(&CsrWaitListsLock);
return Status;
return RtlInitializeCriticalSection(&CsrWaitListsLock);
}
/*++
@ -155,6 +234,7 @@ CsrInsertProcess(IN PCSR_PROCESS Parent OPTIONAL,
{
PCSR_SERVER_DLL ServerDll;
ULONG i;
ASSERT(ProcessStructureListLocked());
/* Set the parent */
CsrProcess->Parent = Parent;
@ -194,15 +274,41 @@ VOID
NTAPI
CsrLockedDereferenceProcess(PCSR_PROCESS CsrProcess)
{
LONG LockCount;
/* Decrease reference count */
if (!(--CsrProcess->ReferenceCount))
LockCount = --CsrProcess->ReferenceCount;
ASSERT(LockCount >= 0);
if (!LockCount)
{
/* Call the generic cleanup code */
CsrAcquireProcessLock();
CsrProcessRefcountZero(CsrProcess);
CsrAcquireProcessLock();
}
}
/*++
* @name CsrLockedReferenceProcess
*
* The CsrLockedReferenceProcess refences a CSR Process while the
* Process Lock is already being held.
*
* @param CsrProcess
* Pointer to the CSR Process to be referenced.
*
* @return None.
*
* @remarks This routine will return with the Process Lock held.
*
*--*/
VOID
NTAPI
CsrLockedReferenceProcess(IN PCSR_PROCESS CsrProcess)
{
/* Increment the reference count */
++CsrProcess->ReferenceCount;
}
/*++
* @name CsrRemoveProcess
*
@ -211,7 +317,7 @@ CsrLockedDereferenceProcess(PCSR_PROCESS CsrProcess)
* of this removal.
*
* @param CsrProcess
* Pointer to the CSR Process to remove.
* Pointer to the CSR Process to remove.
*
* @return None.
*
@ -224,6 +330,7 @@ CsrRemoveProcess(IN PCSR_PROCESS CsrProcess)
{
PCSR_SERVER_DLL ServerDll;
ULONG i;
ASSERT(ProcessStructureListLocked());
/* Remove us from the Process List */
RemoveEntryList(&CsrProcess->ListLink);
@ -279,7 +386,7 @@ CsrProcessRefcountZero(IN PCSR_PROCESS CsrProcess)
}
/* Close the Client Port if there is one */
if (CsrProcess->ClientPort ) NtClose(CsrProcess->ClientPort);
if (CsrProcess->ClientPort) NtClose(CsrProcess->ClientPort);
/* Close the process handle */
NtClose(CsrProcess->ProcessHandle);
@ -289,9 +396,9 @@ CsrProcessRefcountZero(IN PCSR_PROCESS CsrProcess)
}
/*++
* @name CsrSetToNormalPriority
* @name CsrpSetToNormalPriority
*
* The CsrSetToNormalPriority routine sets the current NT Process'
* The CsrpSetToNormalPriority routine sets the current NT Process'
* priority to the normal priority for CSR Processes.
*
* @param None.
@ -304,7 +411,7 @@ CsrProcessRefcountZero(IN PCSR_PROCESS CsrProcess)
*--*/
VOID
NTAPI
CsrSetToNormalPriority(VOID)
CsrpSetToNormalPriority(VOID)
{
KPRIORITY BasePriority = (8 + 1) + 4;
@ -316,9 +423,9 @@ CsrSetToNormalPriority(VOID)
}
/*++
* @name CsrSetToShutdownPriority
* @name CsrpSetToShutdownPriority
*
* The CsrSetToShutdownPriority routine sets the current NT Process'
* The CsrpSetToShutdownPriority routine sets the current NT Process'
* priority to the boosted priority for CSR Processes doing shutdown.
* Additonally, it acquires the Shutdown Privilege required for shutdown.
*
@ -332,7 +439,7 @@ CsrSetToNormalPriority(VOID)
*--*/
VOID
NTAPI
CsrSetToShutdownPriority(VOID)
CsrpSetToShutdownPriority(VOID)
{
KPRIORITY SetBasePriority = (8 + 1) + 6;
BOOLEAN Old;
@ -367,24 +474,20 @@ CsrSetToShutdownPriority(VOID)
*--*/
PCSR_PROCESS
NTAPI
FindProcessForShutdown(PLUID CallerLuid)
FindProcessForShutdown(IN PLUID CallerLuid)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
LUID ProcessLuid;
NTSTATUS Status;
LUID SystemLuid = SYSTEM_LUID;
PCSR_PROCESS CsrProcess;
PCSR_THREAD CsrThread;
BOOLEAN IsSystemLuid = FALSE, IsOurLuid = FALSE;
PCSR_PROCESS ReturnCsrProcess = NULL;
ULONG Level = 0;
/* Set the List Pointers */
ListHead = &CsrRootProcess->ListLink;
NextEntry = ListHead->Flink;
/* Start looping */
while (NextEntry != ListHead)
NextEntry = CsrRootProcess->ListLink.Flink;
while (NextEntry != &CsrRootProcess->ListLink)
{
/* Get the process */
CsrProcess = CONTAINING_RECORD(NextEntry, CSR_PROCESS, ListLink);
@ -422,19 +525,19 @@ FindProcessForShutdown(PLUID CallerLuid)
}
/* Check if this is the System LUID */
if ((IsSystemLuid = RtlEqualLuid(&ProcessLuid, &SystemLuid)))
if (RtlEqualLuid(&ProcessLuid, &SystemLuid))
{
/* Mark this process */
CsrProcess->ShutdownFlags |= CsrShutdownSystem;
}
else if (!(IsOurLuid = RtlEqualLuid(&ProcessLuid, CallerLuid)))
else if (!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)
if ((CsrProcess->ShutdownLevel > Level) || !(ReturnCsrProcess))
{
/* Update the level */
Level = CsrProcess->ShutdownLevel;
@ -468,7 +571,7 @@ FindProcessForShutdown(PLUID CallerLuid)
*
* @param Arguments
* Description of the parameter. Wrapped to more lines on ~70th
* column.
* column.
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
@ -509,19 +612,16 @@ CsrCreateProcess(IN HANDLE hProcess,
}
/* Allocate a new Process Object */
if (!(CsrProcess = CsrAllocateProcess()))
CsrProcess = CsrAllocateProcess();
if (!CsrProcess)
{
/* 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 */
CurrentProcess = CurrentThread->Process;
ProcessData = &CurrentProcess->ServerData[CSR_SERVER_DLL_MAX];
for (i = 0; i < CSR_SERVER_DLL_MAX; i++)
{
@ -540,7 +640,7 @@ CsrCreateProcess(IN HANDLE hProcess,
ProcessData = (PVOID)((ULONG_PTR)ProcessData +
CsrLoadedServerDll[i]->SizeOfProcessData);
}
else
else
{
/* No data for this Server */
CsrProcess->ServerData[i] = NULL;
@ -575,13 +675,13 @@ CsrCreateProcess(IN HANDLE hProcess,
}
/* Check if this is a console process */
if(Flags & CsrProcessIsConsoleApp) CsrProcess->Flags |= CsrProcessIsConsoleApp;
if (Flags & CsrProcessIsConsoleApp) CsrProcess->Flags |= CsrProcessIsConsoleApp;
/* Mask out non-debug flags */
Flags &= ~(CsrProcessIsConsoleApp | CsrProcessCreateNewGroup);
Flags &= ~(CsrProcessIsConsoleApp | CsrProcessCreateNewGroup | CsrProcessPriorityFlags);
/* Check if every process will be debugged */
if (!Flags && CurrentProcess->DebugFlags & CsrDebugProcessChildren)
if (!(Flags) && (CurrentProcess->DebugFlags & CsrDebugProcessChildren))
{
/* Pass it on to the current process */
CsrProcess->DebugFlags = CsrDebugProcessChildren;
@ -589,13 +689,13 @@ CsrCreateProcess(IN HANDLE hProcess,
}
/* Check if Debugging was used on this process */
if (Flags & (CsrDebugOnlyThisProcess | CsrDebugProcessChildren))
if ((Flags & (CsrDebugOnlyThisProcess | CsrDebugProcessChildren)) && (DebugCid))
{
/* Save the debug flag used */
CsrProcess->DebugFlags = Flags;
/* Save the CID */
if (DebugCid) CsrProcess->DebugCid = *DebugCid;
CsrProcess->DebugCid = *DebugCid;
}
/* Check if we debugging is enabled */
@ -606,6 +706,7 @@ CsrCreateProcess(IN HANDLE hProcess,
ProcessDebugPort,
&CsrApiPort,
sizeof(HANDLE));
ASSERT(NT_SUCCESS(Status));
if (!NT_SUCCESS(Status))
{
/* Failed */
@ -621,10 +722,17 @@ CsrCreateProcess(IN HANDLE hProcess,
(PVOID)&KernelTimes,
sizeof(KernelTimes),
NULL);
if (!NT_SUCCESS(Status))
{
/* Failed */
CsrDeallocateProcess(CsrProcess);
CsrReleaseProcessLock();
return STATUS_NO_MEMORY;
}
/* Allocate a CSR Thread Structure */
CsrThread = CsrAllocateThread(CsrProcess);
if (CsrThread == NULL)
if (!CsrThread)
{
/* Failed */
CsrDeallocateProcess(CsrProcess);
@ -636,6 +744,7 @@ CsrCreateProcess(IN HANDLE hProcess,
CsrThread->CreateTime = KernelTimes.CreateTime;
CsrThread->ClientId = *ClientId;
CsrThread->ThreadHandle = hThread;
ProtectHandle(hThread);
CsrThread->Flags = 0;
/* Insert the Thread into the Process */
@ -645,6 +754,11 @@ CsrCreateProcess(IN HANDLE hProcess,
CsrReferenceNtSession(NtSession);
CsrProcess->NtSession = NtSession;
/* Setup Process Data */
CsrProcess->ClientId = *ClientId;
CsrProcess->ProcessHandle = hProcess;
CsrProcess->ShutdownLevel = 0x280;
/* Set the Priority to Background */
CsrSetBackgroundPriority(CsrProcess);
@ -664,7 +778,7 @@ CsrCreateProcess(IN HANDLE hProcess,
* exported only for compatibility with older CSR Server DLLs.
*
* @param CsrProcess
* Deprecated.
* Deprecated.
*
* @return Deprecated
*
@ -673,7 +787,7 @@ CsrCreateProcess(IN HANDLE hProcess,
*--*/
NTSTATUS
NTAPI
CsrDebugProcess(PCSR_PROCESS CsrProcess)
CsrDebugProcess(IN PCSR_PROCESS CsrProcess)
{
/* CSR does not handle debugging anymore */
DPRINT("CSRSRV: %s(%08lx) called\n", __FUNCTION__, CsrProcess);
@ -688,7 +802,7 @@ CsrDebugProcess(PCSR_PROCESS CsrProcess)
* exported only for compatibility with older CSR Server DLLs.
*
* @param CsrProcess
* Deprecated.
* Deprecated.
*
* @return Deprecated
*
@ -697,7 +811,7 @@ CsrDebugProcess(PCSR_PROCESS CsrProcess)
*--*/
NTSTATUS
NTAPI
CsrDebugProcessStop(PCSR_PROCESS CsrProcess)
CsrDebugProcessStop(IN PCSR_PROCESS CsrProcess)
{
/* CSR does not handle debugging anymore */
DPRINT("CSRSRV: %s(%08lx) called\n", __FUNCTION__, CsrProcess);
@ -721,13 +835,17 @@ CsrDebugProcessStop(PCSR_PROCESS CsrProcess)
*--*/
VOID
NTAPI
CsrDereferenceProcess(PCSR_PROCESS CsrProcess)
CsrDereferenceProcess(IN PCSR_PROCESS CsrProcess)
{
LONG LockCount;
/* Acquire process lock */
CsrAcquireProcessLock();
/* Decrease reference count */
if (!(--CsrProcess->ReferenceCount))
LockCount = --CsrProcess->ReferenceCount;
ASSERT(LockCount >= 0);
if (!LockCount)
{
/* Call the generic cleanup code */
CsrProcessRefcountZero(CsrProcess);
@ -743,12 +861,12 @@ CsrDereferenceProcess(PCSR_PROCESS CsrProcess)
* @name CsrDestroyProcess
* @implemented NT4
*
* The CsrDestroyProcess routine destroys the CSR Process corresponding to
* 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.
* Process which is about to be destroyed.
*
* @param ExitStatus
* Unused.
@ -767,17 +885,16 @@ CsrDestroyProcess(IN PCLIENT_ID Cid,
PCSR_THREAD CsrThread;
PCSR_PROCESS CsrProcess;
CLIENT_ID ClientId = *Cid;
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
/* Acquire lock */
CsrAcquireProcessLock();
/* Find the thread */
CsrThread = CsrLocateThreadByClientId(&CsrProcess,
&ClientId);
CsrThread = CsrLocateThreadByClientId(&CsrProcess, &ClientId);
/* Make sure we got one back, and that it's not already gone */
if (!CsrThread || CsrProcess->Flags & CsrProcessTerminating)
if (!(CsrThread) || (CsrProcess->Flags & CsrProcessTerminating))
{
/* Release the lock and return failure */
CsrReleaseProcessLock();
@ -788,20 +905,18 @@ CsrDestroyProcess(IN PCLIENT_ID Cid,
CsrProcess->Flags |= CsrProcessTerminating;
/* Get the List Pointers */
ListHead = &CsrProcess->ThreadList;
NextEntry = ListHead->Flink;
/* Loop the list */
while (NextEntry != ListHead)
NextEntry = CsrProcess->ThreadList.Flink;
while (NextEntry != &CsrProcess->ThreadList)
{
/* 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;
if (CsrThread->Flags & CsrThreadTerminated)
{
NextEntry = NextEntry->Flink;
continue;
}
/* Set the Terminated flag */
CsrThread->Flags |= CsrThreadTerminated;
@ -826,6 +941,7 @@ CsrDestroyProcess(IN PCLIENT_ID Cid,
/* Dereference the thread */
CsrLockedDereferenceThread(CsrThread);
NextEntry = CsrProcess->ThreadList.Flink;
}
/* Release the Process Lock and return success */
@ -843,7 +959,7 @@ CsrDestroyProcess(IN PCLIENT_ID Cid,
* Optional handle to the process whose LUID should be returned.
*
* @param Luid
* Pointer to a LUID Pointer which will receive the CSR Process' LUID
* Pointer to a LUID Pointer which will receive the CSR Process' LUID
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
@ -891,11 +1007,7 @@ CsrGetProcessLuid(HANDLE hProcess OPTIONAL,
Status = NtOpenProcessToken(hProcess,
TOKEN_QUERY,
&hToken);
if (!NT_SUCCESS(Status))
{
/* Still no token, return the error */
return Status;
}
if (!NT_SUCCESS(Status)) return Status;
}
/* Now get the size we'll need for the Token Information */
@ -906,7 +1018,8 @@ CsrGetProcessLuid(HANDLE hProcess OPTIONAL,
&Length);
/* Allocate memory for the Token Info */
if (!(TokenStats = RtlAllocateHeap(CsrHeap, 0, Length)))
TokenStats = RtlAllocateHeap(CsrHeap, 0, Length);
if (!TokenStats)
{
/* Fail and close the token */
NtClose(hToken);
@ -923,12 +1036,8 @@ CsrGetProcessLuid(HANDLE hProcess OPTIONAL,
/* Close the handle */
NtClose(hToken);
/* Check for success */
if (NT_SUCCESS(Status))
{
/* Return the LUID */
*Luid = TokenStats->AuthenticationId;
}
/* Check for success to return the LUID */
if (NT_SUCCESS(Status)) *Luid = TokenStats->AuthenticationId;
/* Free the query information */
RtlFreeHeap(CsrHeap, 0, TokenStats);
@ -961,51 +1070,45 @@ CsrGetProcessLuid(HANDLE hProcess OPTIONAL,
NTSTATUS
NTAPI
CsrLockProcessByClientId(IN HANDLE Pid,
OUT PCSR_PROCESS *CsrProcess OPTIONAL)
OUT PCSR_PROCESS *CsrProcess)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_PROCESS CurrentProcess = NULL;
NTSTATUS Status = STATUS_UNSUCCESSFUL;
/* Acquire the lock */
CsrAcquireProcessLock();
/* Setup the List Pointers */
ListHead = &CsrRootProcess->ListLink;
NextEntry = ListHead;
/* Assume failure */
ASSERT(CsrProcess != NULL);
*CsrProcess = NULL;
/* Start Loop */
while (NextEntry != ListHead)
/* Setup the List Pointers */
NextEntry = CsrRootProcess->ListLink.Flink;
while (NextEntry != &CsrRootProcess->ListLink)
{
/* Get the Process */
CurrentProcess = CONTAINING_RECORD(NextEntry, CSR_PROCESS, ListLink);
/* Check for PID Match */
if (CurrentProcess->ClientId.UniqueProcess == Pid)
{
/* Get out of here with success */
Status = STATUS_SUCCESS;
break;
}
if (CurrentProcess->ClientId.UniqueProcess == Pid) break;
/* Next entry */
NextEntry = NextEntry->Flink;
}
/* Did the loop find something? */
if (NT_SUCCESS(Status))
{
/* Lock the found process */
CurrentProcess->ReferenceCount++;
}
else
/* Check if we didn't find it in the list */
if (NextEntry == &CsrRootProcess->ListLink)
{
/* Nothing found, release the lock */
CsrReleaseProcessLock();
return Status;
}
/* Return the status and process */
if (CsrProcess) *CsrProcess = CurrentProcess;
/* Lock the found process and return it */
Status = STATUS_SUCCESS;
CurrentProcess->ReferenceCount++;
*CsrProcess = CurrentProcess;
return Status;
}
@ -1093,16 +1196,16 @@ CsrSetBackgroundPriority(IN PCSR_PROCESS CsrProcess)
*--*/
NTSTATUS
NTAPI
CsrShutdownProcesses(PLUID CallerLuid,
ULONG Flags)
CsrShutdownProcesses(IN PLUID CallerLuid,
IN ULONG Flags)
{
PLIST_ENTRY ListHead, NextEntry;
PCSR_PROCESS CsrProcess = NULL;
NTSTATUS Status = STATUS_UNSUCCESSFUL;
BOOLEAN FirstTry = TRUE;
ULONG i = 0;
PCSR_SERVER_DLL ServerDll = NULL;
ULONG Result = 0;
PLIST_ENTRY NextEntry;
PCSR_PROCESS CsrProcess;
NTSTATUS Status;
BOOLEAN FirstTry;
ULONG i;
PCSR_SERVER_DLL ServerDll;
ULONG Result;
/* Acquire process lock */
CsrAcquireProcessLock();
@ -1111,11 +1214,8 @@ CsrShutdownProcesses(PLUID CallerLuid,
CsrRootProcess->ShutdownFlags |= CsrShutdownSystem;
/* Get the list pointers */
ListHead = &CsrRootProcess->ListLink;
NextEntry = ListHead->Flink;
/* Start the loop */
while (NextEntry != ListHead)
NextEntry = CsrRootProcess->ListLink.Flink;
while (NextEntry != &CsrRootProcess->ListLink)
{
/* Get the Process */
CsrProcess = CONTAINING_RECORD(NextEntry, CSR_PROCESS, ListLink);
@ -1129,73 +1229,81 @@ CsrShutdownProcesses(PLUID CallerLuid,
}
/* Set shudown Priority */
CsrSetToShutdownPriority();
CsrpSetToShutdownPriority();
/* Start looping */
while (TRUE)
{
/* Find the next process to shutdown */
if (!(CsrProcess = FindProcessForShutdown(CallerLuid)))
{
/* Done, quit */
CsrReleaseProcessLock();
Status = STATUS_SUCCESS;
goto Quickie;
}
CsrProcess = FindProcessForShutdown(CallerLuid);
if (!CsrProcess) break;
/* Increase reference to process */
CsrProcess->ReferenceCount++;
LoopAgain:
/* Loop all the servers */
for (i = 0; i < CSR_SERVER_DLL_MAX; i++)
FirstTry = TRUE;
while (TRUE)
{
/* Get the current server */
ServerDll = CsrLoadedServerDll[i];
if (ServerDll && ServerDll->ShutdownProcessCallback)
/* Loop all the servers */
for (i = 0; i < CSR_SERVER_DLL_MAX; i++)
{
/* Release the lock, make the callback, and acquire it back */
CsrReleaseProcessLock();
Result = (*ServerDll->ShutdownProcessCallback)(CsrProcess,
Flags,
FirstTry);
CsrAcquireProcessLock();
/* Check the result */
if (Result == CsrShutdownCsrProcess)
/* Get the current server */
ServerDll = CsrLoadedServerDll[i];
if ((ServerDll) && (ServerDll->ShutdownProcessCallback))
{
/* The callback unlocked the process */
break;
}
else if (Result == CsrShutdownNonCsrProcess)
{
/* A non-CSR process, the callback didn't touch it */
continue;
}
else if (Result == CsrShutdownCancelled)
{
/* Shutdown was cancelled, unlock and exit */
/* Release the lock, make the callback, and acquire it back */
CsrReleaseProcessLock();
Status = STATUS_CANCELLED;
goto Quickie;
Result = (*ServerDll->ShutdownProcessCallback)(CsrProcess,
Flags,
FirstTry);
CsrAcquireProcessLock();
/* Check the result */
if (Result == CsrShutdownCsrProcess)
{
/* The callback unlocked the process */
break;
}
else if (Result == CsrShutdownCancelled)
{
/* Check if this was a forced shutdown */
if (Flags & EWX_FORCE)
{
DPRINT1("Process %x cancelled forced shutdown (Dll = %d)\n",
CsrProcess->ClientId.UniqueProcess, i);
DbgBreakPoint();
}
/* Shutdown was cancelled, unlock and exit */
CsrReleaseProcessLock();
Status = STATUS_CANCELLED;
goto Quickie;
}
}
}
}
/* No matches during the first try, so loop again */
if (FirstTry && Result == CsrShutdownNonCsrProcess)
{
FirstTry = FALSE;
goto LoopAgain;
/* No matches during the first try, so loop again */
if ((FirstTry) && (Result == CsrShutdownNonCsrProcess))
{
FirstTry = FALSE;
continue;
}
/* Second try, break out */
break;
}
/* We've reached the final loop here, so dereference */
if (i == CSR_SERVER_DLL_MAX) CsrLockedDereferenceProcess(CsrProcess);
}
/* Success path */
CsrReleaseProcessLock();
Status = STATUS_SUCCESS;
Quickie:
/* Return to normal priority */
CsrSetToNormalPriority();
CsrpSetToNormalPriority();
return Status;
}
@ -1206,7 +1314,7 @@ Quickie:
* The CsrUnlockProcess undoes a previous CsrLockProcessByClientId operation.
*
* @param CsrProcess
* Pointer to a previously locked CSR Process.
* Pointer to a previously locked CSR Process.
*
* @return STATUS_SUCCESS.
*
@ -1215,7 +1323,7 @@ Quickie:
*--*/
NTSTATUS
NTAPI
CsrUnlockProcess(PCSR_PROCESS CsrProcess)
CsrUnlockProcess(IN PCSR_PROCESS CsrProcess)
{
/* Dereference the process */
CsrLockedDereferenceProcess(CsrProcess);

View file

@ -78,40 +78,57 @@ CsrLoadServerDll(IN PCHAR DllString,
{
NTSTATUS Status;
ANSI_STRING DllName;
UNICODE_STRING TempString;
UNICODE_STRING TempString, ErrorString;
ULONG_PTR Parameters[2];
HANDLE hServerDll = NULL;
ULONG Size;
PCSR_SERVER_DLL ServerDll;
STRING EntryPointString;
PCSR_SERVER_DLL_INIT_CALLBACK ServerDllInitProcedure;
ULONG Response;
/* Check if it's beyond the maximum we support */
if (ServerId >= CSR_SERVER_DLL_MAX) return(STATUS_TOO_MANY_NAMES);
if (ServerId >= CSR_SERVER_DLL_MAX) return STATUS_TOO_MANY_NAMES;
/* Check if it's already been loaded */
if (CsrLoadedServerDll[ServerId]) return(STATUS_INVALID_PARAMETER);
if (CsrLoadedServerDll[ServerId]) return STATUS_INVALID_PARAMETER;
/* Convert the name to Unicode */
ASSERT(DllString != NULL);
RtlInitAnsiString(&DllName, DllString);
Status = RtlAnsiStringToUnicodeString(&TempString, &DllName, TRUE);
if (!NT_SUCCESS(Status)) return Status;
/* If we are loading ourselves, don't actually load us */
if (ServerId != CSR_SRV_SERVER)
{
/* Load the DLL */
Status = LdrLoadDll(NULL, 0, &TempString, &hServerDll);
if (!NT_SUCCESS(Status))
{
/* Setup error parameters */
Parameters[0] = (ULONG_PTR)&TempString;
Parameters[1] = (ULONG_PTR)&ErrorString;
RtlInitUnicodeString(&ErrorString, L"Default Load Path");
/* Send a hard error */
NtRaiseHardError(Status,
2,
3,
Parameters,
OptionOk,
&Response);
}
/* Get rid of the string */
RtlFreeUnicodeString(&TempString);
if (!NT_SUCCESS(Status))
{
return Status;
}
if (!NT_SUCCESS(Status)) return Status;
}
/* Allocate a CSR DLL Object */
Size = sizeof(CSR_SERVER_DLL) + DllName.MaximumLength;
if (!(ServerDll = RtlAllocateHeap(CsrHeap, HEAP_ZERO_MEMORY, Size)))
ServerDll = RtlAllocateHeap(CsrHeap, HEAP_ZERO_MEMORY, Size);
if (!ServerDll)
{
if (hServerDll) LdrUnloadDll(hServerDll);
return STATUS_NO_MEMORY;
@ -135,7 +152,7 @@ CsrLoadServerDll(IN PCHAR DllString,
if (hServerDll)
{
/* Initialize a string for the entrypoint, or use the default */
RtlInitAnsiString(&EntryPointString,
RtlInitAnsiString(&EntryPointString,
!(EntryPoint) ? "ServerDllInitialization" :
EntryPoint);
@ -255,6 +272,7 @@ CsrSrvClientConnect(IN OUT PCSR_API_MESSAGE ApiMessage,
NTSTATUS Status;
PCSR_CLIENT_CONNECT ClientConnect;
PCSR_SERVER_DLL ServerDll;
PCSR_PROCESS CurrentProcess = ((PCSR_THREAD)NtCurrentTeb()->CsrClientThread)->Process;
/* Load the Message, set default reply */
ClientConnect = (PCSR_CLIENT_CONNECT)&ApiMessage->CsrClientConnect;
@ -287,7 +305,7 @@ CsrSrvClientConnect(IN OUT PCSR_API_MESSAGE ApiMessage,
if (ServerDll->ConnectCallback)
{
/* Call the callback */
Status = (ServerDll->ConnectCallback)(((PCSR_THREAD)NtCurrentTeb()->CsrClientThread)->Process,
Status = (ServerDll->ConnectCallback)(CurrentProcess,
ClientConnect->ConnectionInfo,
&ClientConnect->ConnectionInfoSize);
}
@ -328,12 +346,15 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue)
ULONG ViewSize = 0;
PPEB Peb = NtCurrentPeb();
/* If there's no parameter, fail */
if (ParameterValue) return STATUS_INVALID_PARAMETER;
/* Find the first comma, and null terminate */
while (*SizeValue)
{
if (*SizeValue == ',')
{
*SizeValue++ = '\0';
*SizeValue++ = ANSI_NULL;
break;
}
else
@ -343,12 +364,10 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue)
}
/* Make sure it's valid */
if (!*SizeValue) return(STATUS_INVALID_PARAMETER);
if (!*SizeValue) return STATUS_INVALID_PARAMETER;
/* Convert it to an integer */
Status = RtlCharToInteger(SizeValue,
0,
&Size);
Status = RtlCharToInteger(SizeValue, 0, &Size);
if (!NT_SUCCESS(Status)) return Status;
/* Multiply by 1024 entries and round to page size */
@ -377,7 +396,7 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue)
ViewUnmap,
MEM_TOP_DOWN,
PAGE_EXECUTE_READWRITE);
if(!NT_SUCCESS(Status))
if (!NT_SUCCESS(Status))
{
/* Fail */
NtClose(CsrSrvSharedSection);
@ -390,7 +409,7 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue)
CsrSrvSharedSectionHeap = CsrSrvSharedSectionBase;
/* Create the heap */
if (!(RtlCreateHeap(HEAP_ZERO_MEMORY,
if (!(RtlCreateHeap(HEAP_ZERO_MEMORY | HEAP_CLASS_7,
CsrSrvSharedSectionHeap,
CsrSrvSharedSectionSize,
PAGE_SIZE,
@ -398,8 +417,7 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue)
0)))
{
/* Failure, unmap section and return */
NtUnmapViewOfSection(NtCurrentProcess(),
CsrSrvSharedSectionBase);
NtUnmapViewOfSection(NtCurrentProcess(), CsrSrvSharedSectionBase);
NtClose(CsrSrvSharedSection);
return STATUS_NO_MEMORY;
}
@ -409,6 +427,7 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue)
0,
CSR_SERVER_DLL_MAX *
sizeof(PVOID));
if (!CsrSrvSharedStaticServerData) return STATUS_NO_MEMORY;
/* Write the values to the PEB */
Peb->ReadOnlySharedMemoryBase = CsrSrvSharedSectionBase;
@ -621,7 +640,7 @@ CsrUnhandledExceptionFilter(IN PEXCEPTION_POINTERS ExceptionInfo)
(DebuggerInfo.KernelDebuggerEnabled))
{
/* Call the Unhandled Exception Filter */
if ((Result = RtlUnhandledExceptionFilter(ExceptionInfo)) !=
if ((Result = RtlUnhandledExceptionFilter(ExceptionInfo)) !=
EXCEPTION_CONTINUE_EXECUTION)
{
/* We're going to raise an error. Get Shutdown Privilege first */
@ -656,7 +675,7 @@ CsrUnhandledExceptionFilter(IN PEXCEPTION_POINTERS ExceptionInfo)
OptionShutdownSystem,
&Response);
}
/* Just terminate us */
NtTerminateProcess(NtCurrentProcess(),
ExceptionInfo->ExceptionRecord->ExceptionCode);

View file

@ -14,6 +14,7 @@
#include <debug.h>
/* DATA **********************************************************************/
RTL_CRITICAL_SECTION CsrNtSessionLock;
LIST_ENTRY CsrNtSessionList;
HANDLE CsrSmApiPort;
@ -39,31 +40,28 @@ PCHAR CsrServerSbApiName[5] =
/* PRIVATE FUNCTIONS *********************************************************/
/*++
* @name CsrInitializeNtSessions
* @name CsrInitializeNtSessionList
*
* The CsrInitializeNtSessions routine sets up support for CSR Sessions.
* The CsrInitializeNtSessionList routine sets up support for CSR Sessions.
*
* @param None
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
* @return None
*
* @remarks None.
*
*--*/
NTSTATUS
NTAPI
CsrInitializeNtSessions(VOID)
CsrInitializeNtSessionList(VOID)
{
NTSTATUS Status;
DPRINT("CSRSRV: %s called\n", __FUNCTION__);
/* Initialize the Session List */
InitializeListHead(&CsrNtSessionList);
/* Initialize the Session Lock */
Status = RtlInitializeCriticalSection(&CsrNtSessionLock);
return Status;
return RtlInitializeCriticalSection(&CsrNtSessionLock);
}
/*++
@ -72,7 +70,7 @@ CsrInitializeNtSessions(VOID)
* The CsrAllocateNtSession routine allocates a new CSR NT Session.
*
* @param SessionId
* Session ID of the CSR NT Session to allocate.
* Session ID of the CSR NT Session to allocate.
*
* @return Pointer to the newly allocated CSR NT Session.
*
@ -81,26 +79,27 @@ CsrInitializeNtSessions(VOID)
*--*/
PCSR_NT_SESSION
NTAPI
CsrAllocateNtSession(ULONG SessionId)
CsrAllocateNtSession(IN ULONG SessionId)
{
PCSR_NT_SESSION NtSession;
/* Allocate an NT Session Object */
NtSession = RtlAllocateHeap(CsrHeap,
0,
sizeof(CSR_NT_SESSION));
/* Setup the Session Object */
NtSession = RtlAllocateHeap(CsrHeap, 0, sizeof(CSR_NT_SESSION));
if (NtSession)
{
/* Setup the Session Object */
NtSession->SessionId = SessionId;
NtSession->ReferenceCount = 1;
/* Insert it into the Session List */
CsrAcquireNtSessionLock();
InsertHeadList(&CsrNtSessionList, &NtSession->SessionList);
InsertHeadList(&CsrNtSessionList, &NtSession->SessionLink);
CsrReleaseNtSessionLock();
}
else
{
ASSERT(NtSession != NULL);
}
/* Return the Session (or NULL) */
return NtSession;
@ -112,7 +111,7 @@ CsrAllocateNtSession(ULONG SessionId)
* The CsrReferenceNtSession increases the reference count of a CSR NT Session.
*
* @param Session
* Pointer to the CSR NT Session to reference.
* Pointer to the CSR NT Session to reference.
*
* @return None.
*
@ -121,11 +120,16 @@ CsrAllocateNtSession(ULONG SessionId)
*--*/
VOID
NTAPI
CsrReferenceNtSession(PCSR_NT_SESSION Session)
CsrReferenceNtSession(IN PCSR_NT_SESSION Session)
{
/* Acquire the lock */
CsrAcquireNtSessionLock();
/* Sanity checks */
ASSERT(!IsListEmpty(&Session->SessionLink));
ASSERT(Session->SessionId != 0);
ASSERT(Session->ReferenceCount != 0);
/* Increase the reference count */
Session->ReferenceCount++;
@ -140,8 +144,8 @@ CsrReferenceNtSession(PCSR_NT_SESSION Session)
* CSR NT Session.
*
* @param Session
* Pointer to the CSR NT Session to reference.
*
* Pointer to the CSR NT Session to reference.
*
* @param ExitStatus
* If this is the last reference to the session, this argument
* specifies the exit status.
@ -154,17 +158,22 @@ CsrReferenceNtSession(PCSR_NT_SESSION Session)
*--*/
VOID
NTAPI
CsrDereferenceNtSession(PCSR_NT_SESSION Session,
NTSTATUS ExitStatus)
CsrDereferenceNtSession(IN PCSR_NT_SESSION Session,
IN NTSTATUS ExitStatus)
{
/* Acquire the lock */
CsrAcquireNtSessionLock();
/* Sanity checks */
ASSERT(!IsListEmpty(&Session->SessionLink));
ASSERT(Session->SessionId != 0);
ASSERT(Session->ReferenceCount != 0);
/* Dereference the Session Object */
if (!(--Session->ReferenceCount))
{
/* Remove it from the list */
RemoveEntryList(&Session->SessionList);
RemoveEntryList(&Session->SessionLink);
/* Release the lock */
CsrReleaseNtSessionLock();
@ -202,9 +211,9 @@ CsrDereferenceNtSession(PCSR_NT_SESSION Session,
*--*/
BOOLEAN
NTAPI
CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage)
CsrSbCreateSession(IN PSB_API_MSG ApiMessage)
{
PSB_CREATE_SESSION CreateSession = &ApiMessage->SbCreateSession;
PSB_CREATE_SESSION_MSG CreateSession = &ApiMessage->CreateSession;
HANDLE hProcess, hThread;
PCSR_PROCESS CsrProcess;
NTSTATUS Status;
@ -221,18 +230,15 @@ CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage)
CsrAcquireProcessLock();
/* Allocate a new process */
if (!(CsrProcess = CsrAllocateProcess()))
CsrProcess = CsrAllocateProcess();
if (!CsrProcess)
{
/* Fail */
ApiMessage->Status = STATUS_NO_MEMORY;
ApiMessage->ReturnValue = STATUS_NO_MEMORY;
CsrReleaseProcessLock();
return TRUE;
}
/* Setup Process Data */
CsrProcess->ClientId = CreateSession->ProcessInfo.ClientId;
CsrProcess->ProcessHandle = hProcess;
/* Set the exception port */
Status = NtSetInformationProcess(hProcess,
ProcessExceptionPort,
@ -264,15 +270,17 @@ CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage)
CsrDeallocateProcess(CsrProcess);
CsrReleaseProcessLock();
/* Strange as it seems, NTSTATUSes are actually returned */
return (BOOLEAN)Status;
}
/* Allocate a new Thread */
if (!(CsrThread = CsrAllocateThread(CsrProcess)))
CsrThread = CsrAllocateThread(CsrProcess);
if (!CsrThread)
{
/* Fail the request */
CsrDeallocateProcess(CsrProcess);
ApiMessage->Status = STATUS_NO_MEMORY;
ApiMessage->ReturnValue = STATUS_NO_MEMORY;
CsrReleaseProcessLock();
return TRUE;
}
@ -281,12 +289,15 @@ CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage)
CsrThread->CreateTime = KernelTimes.CreateTime;
CsrThread->ClientId = CreateSession->ProcessInfo.ClientId;
CsrThread->ThreadHandle = hThread;
ProtectHandle(hThread);
CsrThread->Flags = 0;
/* Insert it into the Process List */
CsrInsertThread(CsrProcess, CsrThread);
/* Allocate a new Session */
/* Setup Process Data */
CsrProcess->ClientId = CreateSession->ProcessInfo.ClientId;
CsrProcess->ProcessHandle = hProcess;
CsrProcess->NtSession = CsrAllocateNtSession(CreateSession->SessionId);
/* Set the Process Priority */
@ -319,7 +330,7 @@ CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage)
CsrInsertProcess(NULL, NULL, CsrProcess);
/* Activate the Thread */
ApiMessage->Status = NtResumeThread(hThread, NULL);
ApiMessage->ReturnValue = NtResumeThread(hThread, NULL);
/* Release lock and return */
CsrReleaseProcessLock();
@ -342,10 +353,55 @@ CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage)
*--*/
BOOLEAN
NTAPI
CsrSbForeignSessionComplete(IN PSB_API_MESSAGE ApiMessage)
CsrSbForeignSessionComplete(IN PSB_API_MSG ApiMessage)
{
/* Deprecated/Unimplemented in NT */
ApiMessage->Status = STATUS_NOT_IMPLEMENTED;
ApiMessage->ReturnValue = STATUS_NOT_IMPLEMENTED;
return TRUE;
}
/*++
* @name CsrSbTerminateSession
*
* The CsrSbTerminateSession API is called by the Session Manager
* whenever a foreign session should be destroyed.
*
* @param ApiMessage
* Pointer to the Session Manager API Message.
*
* @return TRUE in case of success, FALSE othwerwise.
*
* @remarks The CsrSbTerminateSession API is not yet implemented.
*
*--*/
BOOLEAN
NTAPI
CsrSbTerminateSession(IN PSB_API_MSG ApiMessage)
{
ApiMessage->ReturnValue = STATUS_NOT_IMPLEMENTED;
return TRUE;
}
/*++
* @name CsrSbCreateProcess
*
* The CsrSbCreateProcess API is called by the Session Manager
* whenever a foreign session is created and a new process should be started.
*
* @param ApiMessage
* Pointer to the Session Manager API Message.
*
* @return TRUE in case of success, FALSE othwerwise.
*
* @remarks The CsrSbCreateProcess API is not yet implemented.
*
*--*/
BOOLEAN
NTAPI
CsrSbCreateProcess(IN PSB_API_MSG ApiMessage)
{
ApiMessage->ReturnValue = STATUS_NOT_IMPLEMENTED;
return TRUE;
}
/* EOF */

View file

@ -10,6 +10,7 @@
/* CSR Header */
#include <csr/server.h>
#include <sm/smmsg.h>
/* PSEH for SEH Support */
#include <pseh/pseh2.h>
@ -38,6 +39,9 @@
#define CsrHashThread(t) \
(HandleToUlong(t)&(256 - 1))
#define ProcessStructureListLocked() \
(CsrProcessLock.OwningThread == NtCurrentTeb()->ClientId.UniqueThread)
#define SM_REG_KEY \
L"\\Registry\\Machine\\System\\CurrentControlSet\\Control\\Session Manager"
@ -72,10 +76,18 @@ extern SYSTEM_BASIC_INFORMATION CsrNtSysInfo;
extern UNICODE_STRING CsrDirectoryName;
extern HANDLE CsrObjectDirectory;
extern PSB_API_ROUTINE CsrServerSbApiDispatch[5];
extern ULONG CsrDebug;
/* FUNCTIONS *****************************************************************/
/* FIXME: Public APIs should go in the CSR Server Include */
BOOLEAN
NTAPI
CsrCaptureArguments(
IN PCSR_THREAD CsrThread,
IN PCSR_API_MESSAGE ApiMessage
);
NTSTATUS
NTAPI
CsrLoadServerDll(
@ -91,6 +103,18 @@ CsrServerInitialization(
PCHAR Arguments[]
);
BOOLEAN
NTAPI
UnProtectHandle(IN HANDLE ObjectHandle);
VOID
NTAPI
CsrLockedReferenceProcess(IN PCSR_PROCESS CsrProcess);
VOID
NTAPI
CsrLockedReferenceThread(IN PCSR_THREAD CsrThread);
NTSTATUS
NTAPI
CsrCreateSessionObjectDirectory(IN ULONG SessionId);
@ -105,11 +129,11 @@ CsrSrvCreateSharedSection(IN PCHAR ParameterValue);
NTSTATUS
NTAPI
CsrInitializeNtSessions(VOID);
CsrInitializeNtSessionList(VOID);
NTSTATUS
NTAPI
CsrInitializeProcesses(VOID);
CsrInitializeProcessStructure(VOID);
NTSTATUS
NTAPI
@ -121,19 +145,19 @@ CsrSbApiPortInitialize(VOID);
BOOLEAN
NTAPI
CsrSbCreateSession(IN PSB_API_MESSAGE ApiMessage);
CsrSbCreateSession(IN PSB_API_MSG ApiMessage);
BOOLEAN
NTAPI
CsrSbTerminateSession(IN PSB_API_MESSAGE ApiMessage);
CsrSbTerminateSession(IN PSB_API_MSG ApiMessage);
BOOLEAN
NTAPI
CsrSbForeignSessionComplete(IN PSB_API_MESSAGE ApiMessage);
CsrSbForeignSessionComplete(IN PSB_API_MSG ApiMessage);
BOOLEAN
NTAPI
CsrSbCreateProcess(IN PSB_API_MESSAGE ApiMessage);
CsrSbCreateProcess(IN PSB_API_MSG ApiMessage);
PCSR_PROCESS
NTAPI
@ -254,6 +278,10 @@ NTSTATUS
NTAPI
CsrApiRequestThread(IN PVOID Parameter);
BOOLEAN
NTAPI
ProtectHandle(IN HANDLE ObjectHandle);
PCSR_THREAD
NTAPI
CsrAddStaticServerThread(
@ -275,7 +303,7 @@ CsrLocateThreadInProcess(
NTSTATUS
NTAPI
CsrSbApiHandleConnectionRequest(IN PSB_API_MESSAGE Message);
CsrSbApiHandleConnectionRequest(IN PSB_API_MSG Message);
NTSTATUS
NTAPI

View file

@ -59,7 +59,7 @@
* CsrMoveSatisfiedWait 753E7909 20 - wait.c - IMPLEMENTED
* CsrNotifyWait 753E782F 21 - wait.c - IMPLEMENTED
* CsrPopulateDosDevices 753E37A5 22 - init.c - IMPLEMENTED
* CsrQueryApiPort 753E4E42 23 - api.c - UNIMPLEMENTED
* CsrQueryApiPort 753E4E42 23 - api.c - IMPLEMENTED
* CsrReferenceThread 753E61E5 24 - thread.c - IMPLEMENTED
* CsrRevertToSelf 753E615A 25 - thread.c - IMPLEMENTED
* CsrServerInitialization 753E3D75 26 - server.c - IMPLEMENTED
@ -93,7 +93,7 @@
* - SMSS needs to be partly re-written to match some things done here.
* Among other things, SmConnectToSm, SmCompleteSession and the other
* Sm* Exported APIs have to be properly implemented, as well as the
* callback calling and SM LPC APIs. [NOT DONE]
* callback calling and SM LPC APIs. [DONE!]
*
* - NTDLL needs to get the Csr* routines properly implemented. [DONE!]
*

View file

@ -47,7 +47,7 @@ CsrAllocateThread(IN PCSR_PROCESS CsrProcess)
/* Allocate the structure */
CsrThread = RtlAllocateHeap(CsrHeap, HEAP_ZERO_MEMORY, sizeof(CSR_THREAD));
if (!CsrThread) return(NULL);
if (!CsrThread) return NULL;
/* Reference the Thread and Process */
CsrThread->ReferenceCount++;
@ -86,24 +86,24 @@ CsrLocateThreadByClientId(OUT PCSR_PROCESS *Process OPTIONAL,
IN PCLIENT_ID ClientId)
{
ULONG i;
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_THREAD FoundThread;
ASSERT(ProcessStructureListLocked());
/* Hash the Thread */
i = CsrHashThread(ClientId->UniqueThread);
/* Set the list pointers */
ListHead = &CsrThreadHashTable[i];
NextEntry = ListHead->Flink;
NextEntry = CsrThreadHashTable[i].Flink;
/* Star the loop */
while (NextEntry != ListHead)
while (NextEntry != &CsrThreadHashTable[i])
{
/* Get the thread */
FoundThread = CONTAINING_RECORD(NextEntry, CSR_THREAD, HashLinks);
/* Compare the CID */
if (FoundThread->ClientId.UniqueThread == ClientId->UniqueThread)
if (*(PULONGLONG)&FoundThread->ClientId == *(PULONGLONG)ClientId)
{
/* Match found, return the process */
*Process = FoundThread->Process;
@ -123,7 +123,7 @@ CsrLocateThreadByClientId(OUT PCSR_PROCESS *Process OPTIONAL,
/*++
* @name CsrLocateThreadInProcess
*
* The CsrLocateThreadInProcess routine locates the CSR Thread
* The CsrLocateThreadInProcess routine locates the CSR Thread
* corresponding to a Client ID inside a specific CSR Process.
*
* @param Process
@ -146,18 +146,17 @@ NTAPI
CsrLocateThreadInProcess(IN PCSR_PROCESS CsrProcess OPTIONAL,
IN PCLIENT_ID Cid)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_THREAD FoundThread = NULL;
/* Use the Root Process if none was specified */
if (!CsrProcess) CsrProcess = CsrRootProcess;
/* Save the List pointers */
ListHead = &CsrProcess->ThreadList;
NextEntry = ListHead->Flink;
NextEntry = CsrProcess->ThreadList.Flink;
/* Start the Loop */
while (NextEntry != ListHead)
while (NextEntry != &CsrProcess->ThreadList)
{
/* Get Thread Entry */
FoundThread = CONTAINING_RECORD(NextEntry, CSR_THREAD, Link);
@ -196,6 +195,7 @@ CsrInsertThread(IN PCSR_PROCESS Process,
IN PCSR_THREAD Thread)
{
ULONG i;
ASSERT(ProcessStructureListLocked());
/* Insert it into the Regular List */
InsertTailList(&Process->ThreadList, &Thread->Link);
@ -230,9 +230,32 @@ NTAPI
CsrDeallocateThread(IN PCSR_THREAD CsrThread)
{
/* Free the process object from the heap */
ASSERT(CsrThread->WaitBlock == NULL);
RtlFreeHeap(CsrHeap, 0, CsrThread);
}
/*++
* @name CsrLockedReferenceThread
*
* The CsrLockedReferenceThread refences a CSR Thread while the
* Process Lock is already being held.
*
* @param CsrThread
* Pointer to the CSR Thread to be referenced.
*
* @return None.
*
* @remarks This routine will return with the Process Lock held.
*
*--*/
VOID
NTAPI
CsrLockedReferenceThread(IN PCSR_THREAD CsrThread)
{
/* Increment the reference count */
++CsrThread->ReferenceCount;
}
/*++
* @name CsrLockedDereferenceThread
*
@ -249,10 +272,14 @@ CsrDeallocateThread(IN PCSR_THREAD CsrThread)
*--*/
VOID
NTAPI
CsrLockedDereferenceThread(PCSR_THREAD CsrThread)
CsrLockedDereferenceThread(IN PCSR_THREAD CsrThread)
{
LONG LockCount;
/* Decrease reference count */
if (!(--CsrThread->ReferenceCount))
LockCount = --CsrThread->ReferenceCount;
ASSERT(LockCount >= 0);
if (!LockCount)
{
/* Call the generic cleanup code */
CsrThreadRefcountZero(CsrThread);
@ -267,7 +294,7 @@ CsrLockedDereferenceThread(PCSR_THREAD CsrThread)
* removes the CSR Thread from the the Hash Table and Thread List.
*
* @param CsrThread
* Pointer to the CSR Thread to remove.
* Pointer to the CSR Thread to remove.
*
* @return None.
*
@ -283,11 +310,13 @@ VOID
NTAPI
CsrRemoveThread(IN PCSR_THREAD CsrThread)
{
ASSERT(ProcessStructureListLocked());
/* Remove it from the List */
RemoveEntryList(&CsrThread->Link);
/* Decreate the thread count of the process */
CsrThread->Process->ThreadCount--;
--CsrThread->Process->ThreadCount;
/* Remove it from the Hash List as well */
if (CsrThread->HashLinks.Flink) RemoveEntryList(&CsrThread->HashLinks);
@ -333,6 +362,7 @@ NTAPI
CsrThreadRefcountZero(IN PCSR_THREAD CsrThread)
{
PCSR_PROCESS CsrProcess = CsrThread->Process;
NTSTATUS Status;
/* Remove this thread */
CsrRemoveThread(CsrThread);
@ -341,8 +371,10 @@ CsrThreadRefcountZero(IN PCSR_THREAD CsrThread)
CsrReleaseProcessLock();
/* Close the NT Thread Handle */
NtClose(CsrThread->ThreadHandle);
UnProtectHandle(CsrThread->ThreadHandle);
Status = NtClose(CsrThread->ThreadHandle);
ASSERT(NT_SUCCESS(Status));
/* De-allocate the CSR Thread Object */
CsrDeallocateThread(CsrThread);
@ -388,10 +420,12 @@ CsrAddStaticServerThread(IN HANDLE hThread,
CsrAcquireProcessLock();
/* Allocate the Server Thread */
if ((CsrThread = CsrAllocateThread(CsrRootProcess)))
CsrThread = CsrAllocateThread(CsrRootProcess);
if (CsrThread)
{
/* Setup the Object */
CsrThread->ThreadHandle = hThread;
ProtectHandle(hThread);
CsrThread->ClientId = *ClientId;
CsrThread->Flags = ThreadFlags;
@ -401,6 +435,10 @@ CsrAddStaticServerThread(IN HANDLE hThread,
/* Increment the thread count */
CsrRootProcess->ThreadCount++;
}
else
{
DPRINT1("CsrAddStaticServerThread: alloc failed for thread 0x%x\n", hThread);
}
/* Release the Process Lock and return */
CsrReleaseProcessLock();
@ -420,7 +458,7 @@ CsrAddStaticServerThread(IN HANDLE hThread,
*
* @param ClientId
* Pointer to the Client ID structure of the NT Thread to associate
* with this CSR Thread.
* with this CSR Thread.
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
@ -444,13 +482,13 @@ CsrCreateRemoteThread(IN HANDLE hThread,
/* Get the Thread Create Time */
Status = NtQueryInformationThread(hThread,
ThreadTimes,
(PVOID)&KernelTimes,
&KernelTimes,
sizeof(KernelTimes),
NULL);
if (!NT_SUCCESS(Status)) return Status;
/* Lock the Owner Process */
Status = CsrLockProcessByClientId(&ClientId->UniqueProcess,
&CsrProcess);
Status = CsrLockProcessByClientId(&ClientId->UniqueProcess, &CsrProcess);
/* Make sure the thread didn't terminate */
if (KernelTimes.ExitTime.QuadPart)
@ -461,7 +499,8 @@ CsrCreateRemoteThread(IN HANDLE hThread,
}
/* Allocate a CSR Thread Structure */
if (!(CsrThread = CsrAllocateThread(CsrProcess)))
CsrThread = CsrAllocateThread(CsrProcess);
if (!CsrThread)
{
DPRINT1("CSRSRV:%s: out of memory!\n", __FUNCTION__);
CsrUnlockProcess(CsrProcess);
@ -483,6 +522,7 @@ CsrCreateRemoteThread(IN HANDLE hThread,
CsrThread->CreateTime = KernelTimes.CreateTime;
CsrThread->ClientId = *ClientId;
CsrThread->ThreadHandle = ThreadHandle;
ProtectHandle(ThreadHandle);
CsrThread->Flags = 0;
/* Insert the Thread into the Process */
@ -508,7 +548,7 @@ CsrCreateRemoteThread(IN HANDLE hThread,
*
* @param ClientId
* Pointer to the Client ID structure of the NT Thread to associate
* with this CSR Thread.
* with this CSR Thread.
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
@ -520,33 +560,38 @@ NTSTATUS
NTAPI
CsrCreateThread(IN PCSR_PROCESS CsrProcess,
IN HANDLE hThread,
IN PCLIENT_ID ClientId)
IN PCLIENT_ID ClientId,
IN BOOLEAN HaveClient)
{
NTSTATUS Status;
PCSR_THREAD CsrThread;
PCSR_THREAD CsrThread, CurrentThread;
PCSR_PROCESS CurrentProcess;
PCSR_THREAD CurrentThread = NtCurrentTeb()->CsrClientThread;
CLIENT_ID CurrentCid;
KERNEL_USER_TIMES KernelTimes;
DPRINT("CSRSRV: %s called\n", __FUNCTION__);
/* Get the current thread and CID */
CurrentCid = CurrentThread->ClientId;
/* Acquire the Process Lock */
CsrAcquireProcessLock();
/* Get the current Process and make sure the Thread is valid with this CID */
CurrentThread = CsrLocateThreadByClientId(&CurrentProcess,
&CurrentCid);
/* Something is wrong if we get an empty thread back */
if (!CurrentThread)
if (HaveClient)
{
DPRINT1("CSRSRV:%s: invalid thread!\n", __FUNCTION__);
CsrReleaseProcessLock();
return STATUS_THREAD_IS_TERMINATING;
/* Get the current thread and CID */
CurrentThread = NtCurrentTeb()->CsrClientThread;
CurrentCid = CurrentThread->ClientId;
/* Acquire the Process Lock */
CsrAcquireProcessLock();
/* Get the current Process and make sure the Thread is valid with this CID */
CurrentThread = CsrLocateThreadByClientId(&CurrentProcess, &CurrentCid);
if (!CurrentThread)
{
DPRINT1("CSRSRV:%s: invalid thread!\n", __FUNCTION__);
CsrReleaseProcessLock();
return STATUS_THREAD_IS_TERMINATING;
}
}
else
{
/* Acquire the Process Lock */
CsrAcquireProcessLock();
}
/* Get the Thread Create Time */
@ -555,9 +600,15 @@ CsrCreateThread(IN PCSR_PROCESS CsrProcess,
(PVOID)&KernelTimes,
sizeof(KernelTimes),
NULL);
if (!NT_SUCCESS(Status))
{
CsrReleaseProcessLock();
return Status;
}
/* Allocate a CSR Thread Structure */
if (!(CsrThread = CsrAllocateThread(CsrProcess)))
CsrThread = CsrAllocateThread(CsrProcess);
if (!CsrThread)
{
DPRINT1("CSRSRV:%s: out of memory!\n", __FUNCTION__);
CsrReleaseProcessLock();
@ -568,6 +619,7 @@ CsrCreateThread(IN PCSR_PROCESS CsrProcess,
CsrThread->CreateTime = KernelTimes.CreateTime;
CsrThread->ClientId = *ClientId;
CsrThread->ThreadHandle = hThread;
ProtectHandle(hThread);
CsrThread->Flags = 0;
/* Insert the Thread into the Process */
@ -595,12 +647,13 @@ CsrCreateThread(IN PCSR_PROCESS CsrProcess,
*--*/
VOID
NTAPI
CsrDereferenceThread(PCSR_THREAD CsrThread)
CsrDereferenceThread(IN PCSR_THREAD CsrThread)
{
/* Acquire process lock */
CsrAcquireProcessLock();
/* Decrease reference count */
ASSERT(CsrThread->ReferenceCount > 0);
if (!(--CsrThread->ReferenceCount))
{
/* Call the generic cleanup code */
@ -624,7 +677,7 @@ CsrDereferenceThread(PCSR_THREAD CsrThread)
* Pointer to the thread's startup routine.
*
* @param Flags
* Initial CSR Thread Flags to set to the CSR Thread.
* Initial CSR Thread Flags to set to the CSR Thread.
*
* @return STATUS_SUCCESS in case of success, STATUS_UNSUCCESSFUL
* othwerwise.
@ -648,7 +701,9 @@ CsrExecServerThread(IN PVOID ThreadHandler,
CsrAcquireProcessLock();
/* Allocate a CSR Thread in the Root Process */
if (!(CsrThread = CsrAllocateThread(CsrRootProcess)))
ASSERT(CsrRootProcess != NULL);
CsrThread = CsrAllocateThread(CsrRootProcess);
if (!CsrThread)
{
/* Fail */
CsrReleaseProcessLock();
@ -676,6 +731,7 @@ CsrExecServerThread(IN PVOID ThreadHandler,
/* Setup the Thread Object */
CsrThread->ThreadHandle = hThread;
ProtectHandle(hThread);
CsrThread->ClientId = ClientId;
CsrThread->Flags = Flags;
@ -694,12 +750,12 @@ CsrExecServerThread(IN PVOID ThreadHandler,
* @name CsrDestroyThread
* @implemented NT4
*
* The CsrDestroyThread routine destroys the CSR Thread corresponding to
* The CsrDestroyThread routine destroys the CSR Thread corresponding to
* a given Thread ID.
*
* @param Cid
* Pointer to the Client ID Structure corresponding to the CSR
* Thread which is about to be destroyed.
* Thread which is about to be destroyed.
*
* @return STATUS_SUCCESS in case of success, STATUS_THREAD_IS_TERMINATING
* if the CSR Thread is already terminating.
@ -766,7 +822,7 @@ CsrDestroyThread(IN PCLIENT_ID Cid)
* The CsrImpersonateClient will impersonate the given CSR Thread.
*
* @param CsrThread
* Pointer to the CSR Thread to impersonate.
* Pointer to the CSR Thread to impersonate.
*
* @return TRUE if impersionation suceeded, false otherwise.
*
@ -784,27 +840,21 @@ CsrImpersonateClient(IN PCSR_THREAD CsrThread)
if (!CsrThread) CsrThread = CurrentThread;
/* Still no thread, something is wrong */
if (!CsrThread)
{
/* Failure */
return FALSE;
}
if (!CsrThread) return FALSE;
/* Make the call */
Status = NtImpersonateThread(NtCurrentThread(),
CsrThread->ThreadHandle,
&CsrSecurityQos);
if (!NT_SUCCESS(Status))
{
/* Failure */
DPRINT1("CSRSS: Can't impersonate client thread - Status = %lx\n", Status);
if (Status != STATUS_BAD_IMPERSONATION_LEVEL) DbgBreakPoint();
return FALSE;
}
/* Increase the impersonation count for the current thread */
/* Increase the impersonation count for the current thread and return */
if (CurrentThread) ++CurrentThread->ImpersonationCount;
/* Return Success */
return TRUE;
}
@ -814,7 +864,7 @@ CsrImpersonateClient(IN PCSR_THREAD CsrThread)
*
* The CsrRevertToSelf routine will attempt to remove an active impersonation.
*
* @param None.
* @param None.
*
* @return TRUE if the reversion was succesful, false otherwise.
*
@ -837,6 +887,8 @@ CsrRevertToSelf(VOID)
/* Make sure impersonation is on */
if (!CurrentThread->ImpersonationCount)
{
DPRINT1("CSRSS: CsrRevertToSelf called while not impersonating\n");
DbgBreakPoint();
return FALSE;
}
else if (--CurrentThread->ImpersonationCount > 0)
@ -853,6 +905,7 @@ CsrRevertToSelf(VOID)
sizeof(HANDLE));
/* Return TRUE or FALSE */
ASSERT(NT_SUCCESS(Status));
return NT_SUCCESS(Status);
}
@ -880,9 +933,9 @@ CsrRevertToSelf(VOID)
NTSTATUS
NTAPI
CsrLockThreadByClientId(IN HANDLE Tid,
OUT PCSR_THREAD *CsrThread OPTIONAL)
OUT PCSR_THREAD *CsrThread)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_THREAD CurrentThread = NULL;
NTSTATUS Status = STATUS_UNSUCCESSFUL;
ULONG i;
@ -890,15 +943,18 @@ CsrLockThreadByClientId(IN HANDLE Tid,
/* Acquire the lock */
CsrAcquireProcessLock();
/* Assume failure */
ASSERT(CsrThread != NULL);
*CsrThread = NULL;
/* Convert to Hash */
i = CsrHashThread(Tid);
/* Setup the List Pointers */
ListHead = &CsrThreadHashTable[i];
NextEntry = ListHead;
NextEntry = CsrThreadHashTable[i].Flink;
/* Start Loop */
while (NextEntry != ListHead)
while (NextEntry != &CsrThreadHashTable[i])
{
/* Get the Process */
CurrentThread = CONTAINING_RECORD(NextEntry, CSR_THREAD, HashLinks);
@ -907,8 +963,7 @@ CsrLockThreadByClientId(IN HANDLE Tid,
if ((CurrentThread->ClientId.UniqueThread == Tid) &&
!(CurrentThread->Flags & CsrThreadTerminated))
{
/* Get out of here with success */
Status = STATUS_SUCCESS;
/* Get out of here */
break;
}
@ -916,20 +971,25 @@ CsrLockThreadByClientId(IN HANDLE Tid,
NextEntry = NextEntry->Flink;
}
/* Nothing found if we got back to the list */
if (NextEntry == &CsrThreadHashTable[i]) CurrentThread = NULL;
/* Did the loop find something? */
if (NT_SUCCESS(Status))
if (CurrentThread)
{
/* Reference the found thread */
Status = STATUS_SUCCESS;
CurrentThread->ReferenceCount++;
*CsrThread = CurrentThread;
}
else
{
/* Nothing found, release the lock */
Status = STATUS_UNSUCCESSFUL;
CsrReleaseProcessLock();
}
/* Return the status and thread */
if (CsrThread) *CsrThread = CurrentThread;
/* Return the status */
return Status;
}
@ -937,11 +997,11 @@ CsrLockThreadByClientId(IN HANDLE Tid,
* @name CsrReferenceThread
* @implemented NT4
*
* The CsrReferenceThread routine increases the active reference count of
* The CsrReferenceThread routine increases the active reference count of
* a CSR Thread.
*
* @param CsrThread
* Pointer to the CSR Thread whose reference count will be increased.
* Pointer to the CSR Thread whose reference count will be increased.
*
* @return None.
*
@ -955,6 +1015,10 @@ CsrReferenceThread(PCSR_THREAD CsrThread)
/* Acquire process lock */
CsrAcquireProcessLock();
/* Sanity checks */
ASSERT(CsrThread->Flags & CsrThreadTerminated); // CSR_THREAD_DESTROYED in ASSERT
ASSERT(CsrThread->ReferenceCount != 0);
/* Increment reference count */
CsrThread->ReferenceCount++;
@ -969,7 +1033,7 @@ CsrReferenceThread(PCSR_THREAD CsrThread)
* The CsrUnlockThread undoes a previous CsrLockThreadByClientId operation.
*
* @param CsrThread
* Pointer to a previously locked CSR Thread.
* Pointer to a previously locked CSR Thread.
*
* @return STATUS_SUCCESS.
*
@ -981,6 +1045,7 @@ NTAPI
CsrUnlockThread(PCSR_THREAD CsrThread)
{
/* Dereference the Thread */
ASSERT(ProcessStructureListLocked());
CsrLockedDereferenceThread(CsrThread);
/* Release the lock and return */

View file

@ -62,7 +62,8 @@ CsrInitializeWait(IN CSR_WAIT_FUNCTION WaitFunction,
WaitApiMessage->Header.u1.s1.TotalLength;
/* Allocate the Wait Block */
if (!(WaitBlock = RtlAllocateHeap(CsrHeap, 0, Size)))
WaitBlock = RtlAllocateHeap(CsrHeap, 0, Size);
if (!WaitBlock)
{
/* Fail */
WaitApiMessage->Status = STATUS_NO_MEMORY;
@ -74,8 +75,9 @@ CsrInitializeWait(IN CSR_WAIT_FUNCTION WaitFunction,
WaitBlock->WaitThread = CsrWaitThread;
WaitBlock->WaitContext = WaitContext;
WaitBlock->WaitFunction = WaitFunction;
InitializeListHead(&WaitBlock->UserWaitList);
InitializeListHead(&WaitBlock->WaitList);
WaitBlock->UserWaitList.Flink = NULL;
WaitBlock->UserWaitList.Blink = NULL;
WaitBlock->WaitList = WaitBlock->UserWaitList;
/* Copy the message */
RtlMoveMemory(&WaitBlock->WaitApiMessage,
@ -173,7 +175,7 @@ CsrNotifyWaitBlock(IN PCSR_WAIT_BLOCK WaitBlock,
WaitBlock->WaitFunction = NULL;
}
/* The wait suceeded*/
/* The wait suceeded */
return TRUE;
}
@ -237,10 +239,9 @@ CsrCreateWait(IN PLIST_ENTRY WaitList,
CsrAcquireWaitLock();
/* Make sure the thread wasn't destroyed */
if (CsrWaitThread && (CsrWaitThread->Flags & CsrThreadTerminated))
if (CsrWaitThread->Flags & CsrThreadTerminated)
{
/* Fail the wait */
CsrWaitThread->WaitBlock = NULL;
RtlFreeHeap(CsrHeap, 0, WaitBlock);
CsrReleaseWaitLock();
return FALSE;
@ -275,7 +276,7 @@ VOID
NTAPI
CsrDereferenceWait(IN PLIST_ENTRY WaitList)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_WAIT_BLOCK WaitBlock;
/* Acquire the Process and Wait Locks */
@ -283,11 +284,10 @@ CsrDereferenceWait(IN PLIST_ENTRY WaitList)
CsrAcquireWaitLock();
/* Set the list pointers */
ListHead = WaitList;
NextEntry = ListHead->Flink;
NextEntry = WaitList->Flink;
/* Start the loop */
while (NextEntry != ListHead)
while (NextEntry != WaitList)
{
/* Get the wait block */
WaitBlock = CONTAINING_RECORD(NextEntry, CSR_WAIT_BLOCK, WaitList);
@ -346,18 +346,17 @@ NTAPI
CsrMoveSatisfiedWait(IN PLIST_ENTRY NewEntry,
IN PLIST_ENTRY WaitList)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_WAIT_BLOCK WaitBlock;
/* Acquire the Wait Lock */
CsrAcquireWaitLock();
/* Set the List pointers */
ListHead = WaitList;
NextEntry = ListHead->Flink;
NextEntry = WaitList->Flink;
/* Start looping */
while (NextEntry != ListHead)
while (NextEntry != WaitList)
{
/* Get the Wait block */
WaitBlock = CONTAINING_RECORD(NextEntry, CSR_WAIT_BLOCK, WaitList);
@ -407,7 +406,7 @@ CsrNotifyWait(IN PLIST_ENTRY WaitList,
IN PVOID WaitArgument1,
IN PVOID WaitArgument2)
{
PLIST_ENTRY ListHead, NextEntry;
PLIST_ENTRY NextEntry;
PCSR_WAIT_BLOCK WaitBlock;
BOOLEAN NotifySuccess = FALSE;
@ -415,11 +414,10 @@ CsrNotifyWait(IN PLIST_ENTRY WaitList,
CsrAcquireWaitLock();
/* Set the List pointers */
ListHead = WaitList;
NextEntry = ListHead->Flink;
NextEntry = WaitList->Flink;
/* Start looping */
while (NextEntry != ListHead)
while (NextEntry != WaitList)
{
/* Get the Wait block */
WaitBlock = CONTAINING_RECORD(NextEntry, CSR_WAIT_BLOCK, WaitList);

View file

@ -1,22 +1,3 @@
/* $Id$
* --------------------------------------------------------------------
*
* This program is free software; you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation; either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along
* with this program; if not, write to the Free Software Foundation, Inc.,
* 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
*
* --------------------------------------------------------------------
*/
/*
* COPYRIGHT: See COPYING in the top level directory
* PROJECT: ReactOS CSR Sub System