3 * reactos/subsys/csrss/api/process.c
5 * "\windows\ApiPort" port process management functions
7 * ReactOS Operating System
10 /* INCLUDES ******************************************************************/
12 #include <ddk/ntddk.h>
14 #include <csrss/csrss.h>
15 #include <ntdll/rtl.h>
18 BOOL STDCALL W32kCleanupForProcess( INT Process );
20 #define LOCK RtlEnterCriticalSection(&ProcessDataLock)
21 #define UNLOCK RtlLeaveCriticalSection(&ProcessDataLock)
23 /* GLOBALS *******************************************************************/
25 static ULONG NrProcess;
26 static PCSRSS_PROCESS_DATA ProcessData[256];
27 extern CRITICAL_SECTION ActiveConsoleLock;
28 CRITICAL_SECTION ProcessDataLock;
30 /* FUNCTIONS *****************************************************************/
32 VOID STDCALL CsrInitProcessData(VOID)
38 ProcessData[i] = NULL;
41 RtlZeroMemory (ProcessData, sizeof ProcessData);
42 NrProcess = sizeof ProcessData / sizeof ProcessData[0];
43 RtlInitializeCriticalSection( &ProcessDataLock );
46 PCSRSS_PROCESS_DATA STDCALL CsrGetProcessData(ULONG ProcessId)
51 for (i=0; i<NrProcess; i++)
54 ProcessData[i]->ProcessId == ProcessId)
57 return(ProcessData[i]);
60 for (i=0; i<NrProcess; i++)
62 if (ProcessData[i] == NULL)
64 ProcessData[i] = RtlAllocateHeap(CsrssApiHeap,
66 sizeof(CSRSS_PROCESS_DATA));
67 if (ProcessData[i] == NULL)
72 ProcessData[i]->ProcessId = ProcessId;
74 return(ProcessData[i]);
77 // DbgPrint("CSR: CsrGetProcessData() failed\n");
82 NTSTATUS STDCALL CsrFreeProcessData(ULONG Pid)
86 for( i = 0; i < NrProcess; i++ )
88 if( ProcessData[i] && ProcessData[i]->ProcessId == Pid )
90 //DbgPrint("CsrFreeProcessData pid: %d\n", Pid);
91 W32kCleanupForProcess( Pid ); //should check if win32k process
92 if( ProcessData[i]->HandleTable )
95 for( c = 0; c < ProcessData[i]->HandleTableSize; c++ )
96 if( ProcessData[i]->HandleTable[c] )
97 CsrReleaseObject( ProcessData[i], (HANDLE)((c + 1) << 2) );
98 RtlFreeHeap( CsrssApiHeap, 0, ProcessData[i]->HandleTable );
100 if( ProcessData[i]->Console )
102 if( InterlockedDecrement( &(ProcessData[i]->Console->Header.ReferenceCount) ) == 0 )
103 CsrDeleteConsole( ProcessData[i]->Console );
105 RtlFreeHeap( CsrssApiHeap, 0, ProcessData[i] );
108 return STATUS_SUCCESS;
112 return STATUS_INVALID_PARAMETER;
116 /**********************************************************************
118 *********************************************************************/
120 CSR_API(CsrCreateProcess)
122 PCSRSS_PROCESS_DATA NewProcessData;
126 Reply->Header.DataSize = sizeof(CSRSS_API_REPLY) -
127 sizeof(LPC_MESSAGE_HEADER);
128 Reply->Header.MessageSize = sizeof(CSRSS_API_REPLY);
130 NewProcessData = CsrGetProcessData(Request->Data.CreateProcessRequest.NewProcessId);
131 if (NewProcessData == NULL)
133 Reply->Status = STATUS_NO_MEMORY;
134 return(STATUS_NO_MEMORY);
137 /* Set default shutdown parameters */
138 NewProcessData->ShutdownLevel = 0x280;
139 NewProcessData->ShutdownFlags = 0;
141 if (Request->Data.CreateProcessRequest.Flags & DETACHED_PROCESS)
143 NewProcessData->Console = NULL;
145 else if (Request->Data.CreateProcessRequest.Flags & CREATE_NEW_CONSOLE)
147 PCSRSS_CONSOLE Console;
149 Console = RtlAllocateHeap(CsrssApiHeap,
151 sizeof(CSRSS_CONSOLE));
152 Status = CsrInitConsole(Console);
153 if( !NT_SUCCESS( Status ) )
155 CsrFreeProcessData( NewProcessData->ProcessId );
156 Reply->Status = Status;
159 NewProcessData->Console = Console;
160 Console->Header.ReferenceCount++;
164 NewProcessData->Console = ProcessData->Console;
165 InterlockedIncrement( &(ProcessData->Console->Header.ReferenceCount) );
168 if( NewProcessData->Console )
171 CsrInsertObject(NewProcessData,
172 &Reply->Data.CreateProcessReply.InputHandle,
173 (Object_t *)NewProcessData->Console);
174 RtlEnterCriticalSection( &ActiveConsoleLock );
175 CsrInsertObject( NewProcessData,
176 &Reply->Data.CreateProcessReply.OutputHandle,
177 &(NewProcessData->Console->ActiveBuffer->Header) );
179 RtlLeaveCriticalSection( &ActiveConsoleLock );
180 ClientId.UniqueProcess = (HANDLE)NewProcessData->ProcessId;
181 Status = NtOpenProcess( &Process, PROCESS_DUP_HANDLE, 0, &ClientId );
182 if( !NT_SUCCESS( Status ) )
184 DbgPrint( "CSR: NtOpenProcess() failed for handle duplication\n" );
185 InterlockedDecrement( &(NewProcessData->Console->Header.ReferenceCount) );
186 CsrFreeProcessData( NewProcessData->ProcessId );
187 Reply->Status = Status;
190 Status = NtDuplicateObject( NtCurrentProcess(), NewProcessData->Console->ActiveEvent, Process, &NewProcessData->ConsoleEvent, SYNCHRONIZE, FALSE, 0 );
191 if( !NT_SUCCESS( Status ) )
193 DbgPrint( "CSR: NtDuplicateObject() failed: %x\n", Status );
195 InterlockedDecrement( &(NewProcessData->Console->Header.ReferenceCount) );
196 CsrFreeProcessData( NewProcessData->ProcessId );
197 Reply->Status = Status;
202 else Reply->Data.CreateProcessReply.OutputHandle = Reply->Data.CreateProcessReply.InputHandle = INVALID_HANDLE_VALUE;
204 return(STATUS_SUCCESS);
207 CSR_API(CsrTerminateProcess)
211 Reply->Header.MessageSize = sizeof(CSRSS_API_REPLY)
212 - sizeof(LPC_MESSAGE_HEADER);
213 Reply->Header.DataSize = sizeof(CSRSS_API_REPLY);
215 Status = CsrFreeProcessData(ProcessData->ProcessId);
217 Reply->Status = Status;
221 CSR_API(CsrConnectProcess)
223 Reply->Header.MessageSize = sizeof(CSRSS_API_REPLY);
224 Reply->Header.DataSize = sizeof(CSRSS_API_REPLY) -
225 sizeof(LPC_MESSAGE_HEADER);
227 Reply->Status = STATUS_SUCCESS;
229 return(STATUS_SUCCESS);
232 CSR_API(CsrGetShutdownParameters)
234 Reply->Header.MessageSize = sizeof(CSRSS_API_REPLY);
235 Reply->Header.DataSize = sizeof(CSRSS_API_REPLY) -
236 sizeof(LPC_MESSAGE_HEADER);
238 Reply->Data.GetShutdownParametersReply.Level = ProcessData->ShutdownLevel;
239 Reply->Data.GetShutdownParametersReply.Flags = ProcessData->ShutdownFlags;
241 Reply->Status = STATUS_SUCCESS;
243 return(STATUS_SUCCESS);
246 CSR_API(CsrSetShutdownParameters)
248 Reply->Header.MessageSize = sizeof(CSRSS_API_REPLY);
249 Reply->Header.DataSize = sizeof(CSRSS_API_REPLY) -
250 sizeof(LPC_MESSAGE_HEADER);
252 ProcessData->ShutdownLevel = Request->Data.SetShutdownParametersRequest.Level;
253 ProcessData->ShutdownFlags = Request->Data.SetShutdownParametersRequest.Flags;
255 Reply->Status = STATUS_SUCCESS;
257 return(STATUS_SUCCESS);