Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygensession.c
Go to the documentation of this file.
00001 /* 00002 * COPYRIGHT: See COPYING in the top level directory 00003 * PROJECT: ReactOS CSR Sub System 00004 * FILE: subsys/csr/csrsrv/session.c 00005 * PURPOSE: CSR Server DLL Session Implementation 00006 * PROGRAMMERS: Alex Ionescu (alex@relsoft.net) 00007 */ 00008 00009 /* INCLUDES ******************************************************************/ 00010 00011 #include "srv.h" 00012 00013 #define NDEBUG 00014 #include <debug.h> 00015 00016 /* DATA **********************************************************************/ 00017 00018 RTL_CRITICAL_SECTION CsrNtSessionLock; 00019 LIST_ENTRY CsrNtSessionList; 00020 HANDLE CsrSmApiPort; 00021 00022 PSB_API_ROUTINE CsrServerSbApiDispatch[5] = 00023 { 00024 CsrSbCreateSession, 00025 CsrSbTerminateSession, 00026 CsrSbForeignSessionComplete, 00027 CsrSbCreateProcess, 00028 NULL 00029 }; 00030 00031 PCHAR CsrServerSbApiName[5] = 00032 { 00033 "SbCreateSession", 00034 "SbTerminateSession", 00035 "SbForeignSessionComplete", 00036 "SbCreateProcess", 00037 "Unknown Csr Sb Api Number" 00038 }; 00039 00040 /* PRIVATE FUNCTIONS *********************************************************/ 00041 00042 /*++ 00043 * @name CsrInitializeNtSessionList 00044 * 00045 * The CsrInitializeNtSessionList routine sets up support for CSR Sessions. 00046 * 00047 * @param None 00048 * 00049 * @return None 00050 * 00051 * @remarks None. 00052 * 00053 *--*/ 00054 NTSTATUS 00055 NTAPI 00056 CsrInitializeNtSessionList(VOID) 00057 { 00058 DPRINT("CSRSRV: %s called\n", __FUNCTION__); 00059 00060 /* Initialize the Session List */ 00061 InitializeListHead(&CsrNtSessionList); 00062 00063 /* Initialize the Session Lock */ 00064 return RtlInitializeCriticalSection(&CsrNtSessionLock); 00065 } 00066 00067 /*++ 00068 * @name CsrAllocateNtSession 00069 * 00070 * The CsrAllocateNtSession routine allocates a new CSR NT Session. 00071 * 00072 * @param SessionId 00073 * Session ID of the CSR NT Session to allocate. 00074 * 00075 * @return Pointer to the newly allocated CSR NT Session. 00076 * 00077 * @remarks None. 00078 * 00079 *--*/ 00080 PCSR_NT_SESSION 00081 NTAPI 00082 CsrAllocateNtSession(IN ULONG SessionId) 00083 { 00084 PCSR_NT_SESSION NtSession; 00085 00086 /* Allocate an NT Session Object */ 00087 NtSession = RtlAllocateHeap(CsrHeap, 0, sizeof(CSR_NT_SESSION)); 00088 if (NtSession) 00089 { 00090 /* Setup the Session Object */ 00091 NtSession->SessionId = SessionId; 00092 NtSession->ReferenceCount = 1; 00093 00094 /* Insert it into the Session List */ 00095 CsrAcquireNtSessionLock(); 00096 InsertHeadList(&CsrNtSessionList, &NtSession->SessionLink); 00097 CsrReleaseNtSessionLock(); 00098 } 00099 else 00100 { 00101 ASSERT(NtSession != NULL); 00102 } 00103 00104 /* Return the Session (or NULL) */ 00105 return NtSession; 00106 } 00107 00108 /*++ 00109 * @name CsrReferenceNtSession 00110 * 00111 * The CsrReferenceNtSession increases the reference count of a CSR NT Session. 00112 * 00113 * @param Session 00114 * Pointer to the CSR NT Session to reference. 00115 * 00116 * @return None. 00117 * 00118 * @remarks None. 00119 * 00120 *--*/ 00121 VOID 00122 NTAPI 00123 CsrReferenceNtSession(IN PCSR_NT_SESSION Session) 00124 { 00125 /* Acquire the lock */ 00126 CsrAcquireNtSessionLock(); 00127 00128 /* Sanity checks */ 00129 ASSERT(!IsListEmpty(&Session->SessionLink)); 00130 ASSERT(Session->SessionId != 0); 00131 ASSERT(Session->ReferenceCount != 0); 00132 00133 /* Increase the reference count */ 00134 Session->ReferenceCount++; 00135 00136 /* Release the lock */ 00137 CsrReleaseNtSessionLock(); 00138 } 00139 00140 /*++ 00141 * @name CsrDereferenceNtSession 00142 * 00143 * The CsrDereferenceNtSession decreases the reference count of a 00144 * CSR NT Session. 00145 * 00146 * @param Session 00147 * Pointer to the CSR NT Session to reference. 00148 * 00149 * @param ExitStatus 00150 * If this is the last reference to the session, this argument 00151 * specifies the exit status. 00152 * 00153 * @return None. 00154 * 00155 * @remarks CsrDereferenceNtSession will complete the session if 00156 * the last reference to it has been closed. 00157 * 00158 *--*/ 00159 VOID 00160 NTAPI 00161 CsrDereferenceNtSession(IN PCSR_NT_SESSION Session, 00162 IN NTSTATUS ExitStatus) 00163 { 00164 /* Acquire the lock */ 00165 CsrAcquireNtSessionLock(); 00166 00167 /* Sanity checks */ 00168 ASSERT(!IsListEmpty(&Session->SessionLink)); 00169 ASSERT(Session->SessionId != 0); 00170 ASSERT(Session->ReferenceCount != 0); 00171 00172 /* Dereference the Session Object */ 00173 if (!(--Session->ReferenceCount)) 00174 { 00175 /* Remove it from the list */ 00176 RemoveEntryList(&Session->SessionLink); 00177 00178 /* Release the lock */ 00179 CsrReleaseNtSessionLock(); 00180 00181 /* Tell SM that we're done here */ 00182 SmSessionComplete(CsrSmApiPort, Session->SessionId, ExitStatus); 00183 00184 /* Free the Session Object */ 00185 RtlFreeHeap(CsrHeap, 0, Session); 00186 } 00187 else 00188 { 00189 /* Release the lock, the Session is still active */ 00190 CsrReleaseNtSessionLock(); 00191 } 00192 } 00193 00194 00195 /* SESSION MANAGER FUNCTIONS**************************************************/ 00196 00197 /*++ 00198 * @name CsrSbCreateSession 00199 * 00200 * The CsrSbCreateSession API is called by the Session Manager whenever a new 00201 * session is created. 00202 * 00203 * @param ApiMessage 00204 * Pointer to the Session Manager API Message. 00205 * 00206 * @return TRUE in case of success, FALSE othwerwise. 00207 * 00208 * @remarks The CsrSbCreateSession routine will initialize a new CSR NT 00209 * Session and allocate a new CSR Process for the subsystem process. 00210 * 00211 *--*/ 00212 BOOLEAN 00213 NTAPI 00214 CsrSbCreateSession(IN PSB_API_MSG ApiMessage) 00215 { 00216 PSB_CREATE_SESSION_MSG CreateSession = &ApiMessage->CreateSession; 00217 HANDLE hProcess, hThread; 00218 PCSR_PROCESS CsrProcess; 00219 NTSTATUS Status; 00220 KERNEL_USER_TIMES KernelTimes; 00221 PCSR_THREAD CsrThread; 00222 PVOID ProcessData; 00223 ULONG i; 00224 00225 /* Save the Process and Thread Handles */ 00226 hProcess = CreateSession->ProcessInfo.ProcessHandle; 00227 hThread = CreateSession->ProcessInfo.ThreadHandle; 00228 00229 /* Lock the Processes */ 00230 CsrAcquireProcessLock(); 00231 00232 /* Allocate a new process */ 00233 CsrProcess = CsrAllocateProcess(); 00234 if (!CsrProcess) 00235 { 00236 /* Fail */ 00237 ApiMessage->ReturnValue = STATUS_NO_MEMORY; 00238 CsrReleaseProcessLock(); 00239 return TRUE; 00240 } 00241 00242 /* Set the exception port */ 00243 Status = NtSetInformationProcess(hProcess, 00244 ProcessExceptionPort, 00245 &CsrApiPort, 00246 sizeof(HANDLE)); 00247 00248 /* Check for success */ 00249 if (!NT_SUCCESS(Status)) 00250 { 00251 /* Fail the request */ 00252 CsrDeallocateProcess(CsrProcess); 00253 CsrReleaseProcessLock(); 00254 00255 /* Strange as it seems, NTSTATUSes are actually returned */ 00256 return (BOOLEAN)STATUS_NO_MEMORY; 00257 } 00258 00259 /* Get the Create Time */ 00260 Status = NtQueryInformationThread(hThread, 00261 ThreadTimes, 00262 &KernelTimes, 00263 sizeof(KERNEL_USER_TIMES), 00264 NULL); 00265 00266 /* Check for success */ 00267 if (!NT_SUCCESS(Status)) 00268 { 00269 /* Fail the request */ 00270 CsrDeallocateProcess(CsrProcess); 00271 CsrReleaseProcessLock(); 00272 00273 /* Strange as it seems, NTSTATUSes are actually returned */ 00274 return (BOOLEAN)Status; 00275 } 00276 00277 /* Allocate a new Thread */ 00278 CsrThread = CsrAllocateThread(CsrProcess); 00279 if (!CsrThread) 00280 { 00281 /* Fail the request */ 00282 CsrDeallocateProcess(CsrProcess); 00283 ApiMessage->ReturnValue = STATUS_NO_MEMORY; 00284 CsrReleaseProcessLock(); 00285 return TRUE; 00286 } 00287 00288 /* Setup the Thread Object */ 00289 CsrThread->CreateTime = KernelTimes.CreateTime; 00290 CsrThread->ClientId = CreateSession->ProcessInfo.ClientId; 00291 CsrThread->ThreadHandle = hThread; 00292 ProtectHandle(hThread); 00293 CsrThread->Flags = 0; 00294 00295 /* Insert it into the Process List */ 00296 CsrInsertThread(CsrProcess, CsrThread); 00297 00298 /* Setup Process Data */ 00299 CsrProcess->ClientId = CreateSession->ProcessInfo.ClientId; 00300 CsrProcess->ProcessHandle = hProcess; 00301 CsrProcess->NtSession = CsrAllocateNtSession(CreateSession->SessionId); 00302 00303 /* Set the Process Priority */ 00304 CsrSetBackgroundPriority(CsrProcess); 00305 00306 /* Get the first data location */ 00307 ProcessData = &CsrProcess->ServerData[CSR_SERVER_DLL_MAX]; 00308 00309 /* Loop every DLL */ 00310 for (i = 0; i < CSR_SERVER_DLL_MAX; i++) 00311 { 00312 /* Check if the DLL is loaded and has Process Data */ 00313 if (CsrLoadedServerDll[i] && CsrLoadedServerDll[i]->SizeOfProcessData) 00314 { 00315 /* Write the pointer to the data */ 00316 CsrProcess->ServerData[i] = ProcessData; 00317 00318 /* Move to the next data location */ 00319 ProcessData = (PVOID)((ULONG_PTR)ProcessData + 00320 CsrLoadedServerDll[i]->SizeOfProcessData); 00321 } 00322 else 00323 { 00324 /* Nothing for this Process */ 00325 CsrProcess->ServerData[i] = NULL; 00326 } 00327 } 00328 00329 /* Insert the Process */ 00330 CsrInsertProcess(NULL, NULL, CsrProcess); 00331 00332 /* Activate the Thread */ 00333 ApiMessage->ReturnValue = NtResumeThread(hThread, NULL); 00334 00335 /* Release lock and return */ 00336 CsrReleaseProcessLock(); 00337 return TRUE; 00338 } 00339 00340 /*++ 00341 * @name CsrSbForeignSessionComplete 00342 * 00343 * The CsrSbForeignSessionComplete API is called by the Session Manager 00344 * whenever a foreign session is completed (ie: terminated). 00345 * 00346 * @param ApiMessage 00347 * Pointer to the Session Manager API Message. 00348 * 00349 * @return TRUE in case of success, FALSE othwerwise. 00350 * 00351 * @remarks The CsrSbForeignSessionComplete API is not yet implemented. 00352 * 00353 *--*/ 00354 BOOLEAN 00355 NTAPI 00356 CsrSbForeignSessionComplete(IN PSB_API_MSG ApiMessage) 00357 { 00358 /* Deprecated/Unimplemented in NT */ 00359 ApiMessage->ReturnValue = STATUS_NOT_IMPLEMENTED; 00360 return TRUE; 00361 } 00362 00363 /*++ 00364 * @name CsrSbTerminateSession 00365 * 00366 * The CsrSbTerminateSession API is called by the Session Manager 00367 * whenever a foreign session should be destroyed. 00368 * 00369 * @param ApiMessage 00370 * Pointer to the Session Manager API Message. 00371 * 00372 * @return TRUE in case of success, FALSE othwerwise. 00373 * 00374 * @remarks The CsrSbTerminateSession API is not yet implemented. 00375 * 00376 *--*/ 00377 BOOLEAN 00378 NTAPI 00379 CsrSbTerminateSession(IN PSB_API_MSG ApiMessage) 00380 { 00381 ApiMessage->ReturnValue = STATUS_NOT_IMPLEMENTED; 00382 return TRUE; 00383 } 00384 00385 /*++ 00386 * @name CsrSbCreateProcess 00387 * 00388 * The CsrSbCreateProcess API is called by the Session Manager 00389 * whenever a foreign session is created and a new process should be started. 00390 * 00391 * @param ApiMessage 00392 * Pointer to the Session Manager API Message. 00393 * 00394 * @return TRUE in case of success, FALSE othwerwise. 00395 * 00396 * @remarks The CsrSbCreateProcess API is not yet implemented. 00397 * 00398 *--*/ 00399 BOOLEAN 00400 NTAPI 00401 CsrSbCreateProcess(IN PSB_API_MSG ApiMessage) 00402 { 00403 ApiMessage->ReturnValue = STATUS_NOT_IMPLEMENTED; 00404 return TRUE; 00405 } 00406 00407 /* EOF */ Generated on Thu May 24 2012 04:24:46 for ReactOS by
1.7.6.1
|