[HEADERS]
[reactos.git] / reactos / win32ss / user / winsrv / usersrv / init.c
1 /*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: ReactOS User API Server DLL
4 * FILE: win32ss/user/winsrv/usersrv/init.c
5 * PURPOSE: Initialization
6 * PROGRAMMERS: Dmitry Philippov (shedon@mail.ru)
7 * Hermes Belusca-Maito (hermes.belusca@sfr.fr)
8 */
9
10 /* INCLUDES *******************************************************************/
11
12 #include "usersrv.h"
13
14 #include "api.h"
15
16 #define NDEBUG
17 #include <debug.h>
18
19 /* GLOBALS ********************************************************************/
20
21 HINSTANCE UserServerDllInstance = NULL;
22
23 /* Handles for Power and Media events. Used by both usersrv and win32k. */
24 HANDLE ghPowerRequestEvent;
25 HANDLE ghMediaRequestEvent;
26
27 /* Copy of CSR Port handle for win32k */
28 HANDLE CsrApiPort = NULL;
29
30 /* Memory */
31 HANDLE UserServerHeap = NULL; // Our own heap.
32
33 // Windows Server 2003 table from http://j00ru.vexillium.org/csrss_list/api_list.html#Windows_2k3
34 PCSR_API_ROUTINE UserServerApiDispatchTable[UserpMaxApiNumber - USERSRV_FIRST_API_NUMBER] =
35 {
36 SrvExitWindowsEx,
37 SrvEndTask,
38 SrvLogon,
39 SrvRegisterServicesProcess, // Not present in Win7
40 SrvActivateDebugger,
41 SrvGetThreadConsoleDesktop, // Not present in Win7
42 SrvDeviceEvent,
43 SrvRegisterLogonProcess, // Not present in Win7
44 SrvCreateSystemThreads,
45 SrvRecordShutdownReason,
46 // SrvCancelShutdown, // Added in Vista
47 // SrvConsoleHandleOperation, // Added in Win7
48 // SrvGetSetShutdownBlockReason, // Added in Vista
49 };
50
51 BOOLEAN UserServerApiServerValidTable[UserpMaxApiNumber - USERSRV_FIRST_API_NUMBER] =
52 {
53 FALSE, // SrvExitWindowsEx
54 FALSE, // SrvEndTask
55 FALSE, // SrvLogon
56 FALSE, // SrvRegisterServicesProcess
57 FALSE, // SrvActivateDebugger
58 TRUE, // SrvGetThreadConsoleDesktop
59 FALSE, // SrvDeviceEvent
60 FALSE, // SrvRegisterLogonProcess
61 FALSE, // SrvCreateSystemThreads
62 FALSE, // SrvRecordShutdownReason
63 // FALSE, // SrvCancelShutdown
64 // FALSE, // SrvConsoleHandleOperation
65 // FALSE, // SrvGetSetShutdownBlockReason
66 };
67
68 /*
69 * On Windows Server 2003, CSR Servers contain
70 * the API Names Table only in Debug Builds.
71 */
72 #ifdef CSR_DBG
73 PCHAR UserServerApiNameTable[UserpMaxApiNumber - USERSRV_FIRST_API_NUMBER] =
74 {
75 "SrvExitWindowsEx",
76 "SrvEndTask",
77 "SrvLogon",
78 "SrvRegisterServicesProcess",
79 "SrvActivateDebugger",
80 "SrvGetThreadConsoleDesktop",
81 "SrvDeviceEvent",
82 "SrvRegisterLogonProcess",
83 "SrvCreateSystemThreads",
84 "SrvRecordShutdownReason",
85 // "SrvCancelShutdown",
86 // "SrvConsoleHandleOperation",
87 // "SrvGetSetShutdownBlockReason",
88 };
89 #endif
90
91 /* FUNCTIONS ******************************************************************/
92
93 // PUSER_SOUND_SENTRY. Used in basesrv.dll
94 BOOL NTAPI _UserSoundSentry(VOID)
95 {
96 // TODO: Do something.
97 return TRUE;
98 }
99
100 ULONG
101 NTAPI
102 CreateSystemThreads(PVOID pParam)
103 {
104 NtUserCallOneParam((DWORD)pParam, ONEPARAM_ROUTINE_CREATESYSTEMTHREADS);
105 DPRINT1("This thread should not terminate!\n");
106 return 0;
107 }
108
109 CSR_API(SrvCreateSystemThreads)
110 {
111 DPRINT1("%s not yet implemented\n", __FUNCTION__);
112 return STATUS_NOT_IMPLEMENTED;
113 }
114
115 CSR_API(SrvActivateDebugger)
116 {
117 DPRINT1("%s not yet implemented\n", __FUNCTION__);
118 return STATUS_NOT_IMPLEMENTED;
119 }
120
121 CSR_API(SrvGetThreadConsoleDesktop)
122 {
123 PUSER_GET_THREAD_CONSOLE_DESKTOP GetThreadConsoleDesktopRequest = &((PUSER_API_MESSAGE)ApiMessage)->Data.GetThreadConsoleDesktopRequest;
124
125 DPRINT1("%s not yet implemented\n", __FUNCTION__);
126
127 /* Return nothing for the moment... */
128 GetThreadConsoleDesktopRequest->ConsoleDesktop = NULL;
129
130 /* Always succeeds */
131 return STATUS_SUCCESS;
132 }
133
134 CSR_API(SrvDeviceEvent)
135 {
136 DPRINT1("%s not yet implemented\n", __FUNCTION__);
137 return STATUS_NOT_IMPLEMENTED;
138 }
139
140 NTSTATUS
141 NTAPI
142 UserClientConnect(IN PCSR_PROCESS CsrProcess,
143 IN OUT PVOID ConnectionInfo,
144 IN OUT PULONG ConnectionInfoLength)
145 {
146 NTSTATUS Status;
147 // PUSERCONNECT
148 PUSERSRV_API_CONNECTINFO ConnectInfo = (PUSERSRV_API_CONNECTINFO)ConnectionInfo;
149
150 DPRINT1("UserClientConnect\n");
151
152 /* Check if we don't have an API port yet */
153 if (CsrApiPort == NULL)
154 {
155 /* Query the API port and save it globally */
156 CsrApiPort = CsrQueryApiPort();
157
158 /* Inform win32k about the API port */
159 Status = NtUserSetInformationThread(NtCurrentThread(),
160 UserThreadCsrApiPort,
161 &CsrApiPort,
162 sizeof(CsrApiPort));
163 if (!NT_SUCCESS(Status))
164 {
165 return Status;
166 }
167 }
168
169 /* Check connection info validity */
170 if ( ConnectionInfo == NULL ||
171 ConnectionInfoLength == NULL ||
172 *ConnectionInfoLength != sizeof(*ConnectInfo) )
173 {
174 DPRINT1("USERSRV: Connection failed - ConnectionInfo = 0x%p ; ConnectionInfoLength = 0x%p (%lu), expected %lu\n",
175 ConnectionInfo,
176 ConnectionInfoLength,
177 ConnectionInfoLength ? *ConnectionInfoLength : (ULONG)-1,
178 sizeof(*ConnectInfo));
179
180 return STATUS_INVALID_PARAMETER;
181 }
182
183 /* Pass the request to win32k */
184 ConnectInfo->dwDispatchCount = 0; // gDispatchTableValues;
185 Status = NtUserProcessConnect(CsrProcess->ProcessHandle,
186 ConnectInfo,
187 *ConnectionInfoLength);
188
189 return Status;
190 }
191
192 CSR_SERVER_DLL_INIT(UserServerDllInitialization)
193 {
194 /*** From win32csr... ***/
195 HANDLE ServerThread;
196 CLIENT_ID ClientId;
197 NTSTATUS Status;
198 UINT i;
199 /*** END - From win32csr... ***/
200
201 /* Initialize the memory */
202 UserServerHeap = RtlGetProcessHeap();
203
204 /* Setup the DLL Object */
205 LoadedServerDll->ApiBase = USERSRV_FIRST_API_NUMBER;
206 LoadedServerDll->HighestApiSupported = UserpMaxApiNumber;
207 LoadedServerDll->DispatchTable = UserServerApiDispatchTable;
208 LoadedServerDll->ValidTable = UserServerApiServerValidTable;
209 #ifdef CSR_DBG
210 LoadedServerDll->NameTable = UserServerApiNameTable;
211 #endif
212 LoadedServerDll->SizeOfProcessData = 0;
213 LoadedServerDll->ConnectCallback = UserClientConnect;
214 LoadedServerDll->DisconnectCallback = NULL;
215 LoadedServerDll->HardErrorCallback = UserServerHardError;
216 LoadedServerDll->ShutdownProcessCallback = UserClientShutdown;
217
218 UserServerDllInstance = LoadedServerDll->ServerHandle;
219
220 /*** From win32csr... See r54125 ***/
221 /* Start the Raw Input Thread and the Desktop Thread */
222 for (i = 0; i < 2; ++i)
223 {
224 Status = RtlCreateUserThread(NtCurrentProcess(),
225 NULL, TRUE, 0, 0, 0,
226 CreateSystemThreads,
227 (PVOID)i, &ServerThread, &ClientId);
228 if (NT_SUCCESS(Status))
229 {
230 NtResumeThread(ServerThread, NULL);
231 NtClose(ServerThread);
232 }
233 else
234 {
235 DPRINT1("Cannot start Raw Input Thread!\n");
236 }
237 }
238 /*** END - From win32csr... ***/
239
240 /* Create the power request event */
241 Status = NtCreateEvent(&ghPowerRequestEvent,
242 EVENT_ALL_ACCESS,
243 NULL,
244 SynchronizationEvent,
245 FALSE);
246 if (!NT_SUCCESS(Status))
247 {
248 DPRINT1("Power request event creation failed with Status 0x%08x\n", Status);
249 return Status;
250 }
251
252 /* Create the media request event */
253 Status = NtCreateEvent(&ghMediaRequestEvent,
254 EVENT_ALL_ACCESS,
255 NULL,
256 SynchronizationEvent,
257 FALSE);
258 if (!NT_SUCCESS(Status))
259 {
260 DPRINT1("Media request event creation failed with Status 0x%08x\n", Status);
261 return Status;
262 }
263
264 /* Initialize the kernel mode subsystem */
265 Status = NtUserInitialize(USER_VERSION,
266 ghPowerRequestEvent,
267 ghMediaRequestEvent);
268 if (!NT_SUCCESS(Status))
269 {
270 DPRINT1("NtUserInitialize failed with Status 0x%08x\n", Status);
271 return Status;
272 }
273
274 /* All done */
275 return STATUS_SUCCESS;
276 }
277
278 /* EOF */