* Sync up to trunk HEAD (r62286).
[reactos.git] / dll / win32 / samsrv / samsrv.c
1 /*
2 * SAM Server DLL
3 * Copyright (C) 2005 Eric Kohl
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 * GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License along
16 * with this program; if not, write to the Free Software Foundation, Inc.,
17 * 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA.
18 */
19
20 #include "samsrv.h"
21
22 #include <samsrv/samsrv.h>
23
24 /* GLOBALS *******************************************************************/
25
26 ENCRYPTED_NT_OWF_PASSWORD EmptyNtHash;
27 ENCRYPTED_LM_OWF_PASSWORD EmptyLmHash;
28 RTL_RESOURCE SampResource;
29
30
31 /* FUNCTIONS *****************************************************************/
32
33 static
34 NTSTATUS
35 SampInitHashes(VOID)
36 {
37 UNICODE_STRING EmptyNtPassword = {0, 0, NULL};
38 CHAR EmptyLmPassword[15] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,};
39 NTSTATUS Status;
40
41 /* Calculate the NT hash value of the empty password */
42 Status = SystemFunction007(&EmptyNtPassword,
43 (LPBYTE)&EmptyNtHash);
44 if (!NT_SUCCESS(Status))
45 {
46 ERR("Calculation of the empty NT hash failed (Status 0x%08lx)\n", Status);
47 return Status;
48 }
49
50 /* Calculate the LM hash value of the empty password */
51 Status = SystemFunction006(EmptyLmPassword,
52 (LPSTR)&EmptyLmHash);
53 if (!NT_SUCCESS(Status))
54 {
55 ERR("Calculation of the empty LM hash failed (Status 0x%08lx)\n", Status);
56 }
57
58 return Status;
59 }
60
61
62 NTSTATUS
63 NTAPI
64 SamIConnect(IN PSAMPR_SERVER_NAME ServerName,
65 OUT SAMPR_HANDLE *ServerHandle,
66 IN ACCESS_MASK DesiredAccess,
67 IN BOOLEAN Trusted)
68 {
69 PSAM_DB_OBJECT ServerObject;
70 NTSTATUS Status;
71
72 TRACE("SamIConnect(%p %p %lx %ld)\n",
73 ServerName, ServerHandle, DesiredAccess, Trusted);
74
75 /* Map generic access rights */
76 RtlMapGenericMask(&DesiredAccess,
77 pServerMapping);
78
79 /* Open the Server Object */
80 Status = SampOpenDbObject(NULL,
81 NULL,
82 L"SAM",
83 0,
84 SamDbServerObject,
85 DesiredAccess,
86 &ServerObject);
87 if (NT_SUCCESS(Status))
88 {
89 ServerObject->Trusted = Trusted;
90 *ServerHandle = (SAMPR_HANDLE)ServerObject;
91 }
92
93 TRACE("SamIConnect done (Status 0x%08lx)\n", Status);
94
95 return Status;
96 }
97
98
99 NTSTATUS
100 NTAPI
101 SamIInitialize(VOID)
102 {
103 NTSTATUS Status = STATUS_SUCCESS;
104
105 TRACE("SamIInitialize() called\n");
106
107 Status = SampInitHashes();
108 if (!NT_SUCCESS(Status))
109 return Status;
110
111 if (SampIsSetupRunning())
112 {
113 Status = SampInitializeRegistry();
114 if (!NT_SUCCESS(Status))
115 return Status;
116 }
117
118 RtlInitializeResource(&SampResource);
119
120 /* Initialize the SAM database */
121 Status = SampInitDatabase();
122 if (!NT_SUCCESS(Status))
123 return Status;
124
125 /* Start the RPC server */
126 SampStartRpcServer();
127
128 return Status;
129 }
130
131
132 NTSTATUS
133 NTAPI
134 SampInitializeRegistry(VOID)
135 {
136 TRACE("SampInitializeRegistry() called\n");
137
138 SampInitializeSAM();
139
140 return STATUS_SUCCESS;
141 }
142
143
144 VOID
145 NTAPI
146 SamIFreeVoid(PVOID Ptr)
147 {
148 MIDL_user_free(Ptr);
149 }
150
151
152 VOID
153 NTAPI
154 SamIFree_SAMPR_ENUMERATION_BUFFER(PSAMPR_ENUMERATION_BUFFER Ptr)
155 {
156 ULONG i;
157
158 if (Ptr != NULL)
159 {
160 if (Ptr->Buffer != NULL)
161 {
162 for (i = 0; i < Ptr->EntriesRead; i++)
163 {
164 if (Ptr->Buffer[i].Name.Buffer != NULL)
165 MIDL_user_free(Ptr->Buffer[i].Name.Buffer);
166 }
167
168 MIDL_user_free(Ptr->Buffer);
169 }
170
171 MIDL_user_free(Ptr);
172 }
173 }
174
175
176 VOID
177 NTAPI
178 SamIFree_SAMPR_GET_GROUPS_BUFFER(PSAMPR_GET_GROUPS_BUFFER Ptr)
179 {
180 if (Ptr != NULL)
181 {
182 if (Ptr->Groups != NULL)
183 MIDL_user_free(Ptr->Groups);
184
185 MIDL_user_free(Ptr);
186 }
187 }
188
189
190 VOID
191 NTAPI
192 SamIFree_SAMPR_GET_MEMBERS_BUFFER(PSAMPR_GET_MEMBERS_BUFFER Ptr)
193 {
194 if (Ptr != NULL)
195 {
196 if (Ptr->Members != NULL)
197 MIDL_user_free(Ptr->Members);
198
199 if (Ptr->Attributes != NULL)
200 MIDL_user_free(Ptr->Attributes);
201
202 MIDL_user_free(Ptr);
203 }
204 }
205
206
207 VOID
208 NTAPI
209 SamIFree_SAMPR_PSID_ARRAY(PSAMPR_PSID_ARRAY Ptr)
210 {
211 if (Ptr != NULL)
212 {
213 if (Ptr->Sids != NULL)
214 {
215 MIDL_user_free(Ptr->Sids);
216 }
217 }
218 }
219
220
221 VOID
222 NTAPI
223 SamIFree_SAMPR_RETURNED_USTRING_ARRAY(PSAMPR_RETURNED_USTRING_ARRAY Ptr)
224 {
225 ULONG i;
226
227 if (Ptr != NULL)
228 {
229 if (Ptr->Element != NULL)
230 {
231 for (i = 0; i < Ptr->Count; i++)
232 {
233 if (Ptr->Element[i].Buffer != NULL)
234 MIDL_user_free(Ptr->Element[i].Buffer);
235 }
236
237 MIDL_user_free(Ptr->Element);
238 Ptr->Element = NULL;
239 Ptr->Count = 0;
240 }
241 }
242 }
243
244
245 VOID
246 NTAPI
247 SamIFree_SAMPR_SR_SECURITY_DESCRIPTOR(PSAMPR_SR_SECURITY_DESCRIPTOR Ptr)
248 {
249 if (Ptr != NULL)
250 {
251 if (Ptr->SecurityDescriptor != NULL)
252 MIDL_user_free(Ptr->SecurityDescriptor);
253
254 MIDL_user_free(Ptr);
255 }
256 }
257
258
259 VOID
260 NTAPI
261 SamIFree_SAMPR_ULONG_ARRAY(PSAMPR_ULONG_ARRAY Ptr)
262 {
263 if (Ptr != NULL)
264 {
265 if (Ptr->Element != NULL)
266 {
267 MIDL_user_free(Ptr->Element);
268 Ptr->Element = NULL;
269 Ptr->Count = 0;
270 }
271 }
272 }
273
274
275 VOID
276 NTAPI
277 SamIFree_SAMPR_USER_INFO_BUFFER(PSAMPR_USER_INFO_BUFFER Ptr,
278 USER_INFORMATION_CLASS InformationClass)
279 {
280 if (Ptr == NULL)
281 return;
282
283 switch (InformationClass)
284 {
285 case UserGeneralInformation:
286 if (Ptr->General.UserName.Buffer != NULL)
287 MIDL_user_free(Ptr->General.UserName.Buffer);
288
289 if (Ptr->General.FullName.Buffer != NULL)
290 MIDL_user_free(Ptr->General.FullName.Buffer);
291
292 if (Ptr->General.AdminComment.Buffer != NULL)
293 MIDL_user_free(Ptr->General.AdminComment.Buffer);
294
295 if (Ptr->General.UserComment.Buffer != NULL)
296 MIDL_user_free(Ptr->General.UserComment.Buffer);
297 break;
298
299 case UserPreferencesInformation:
300 if (Ptr->Preferences.UserComment.Buffer != NULL)
301 MIDL_user_free(Ptr->Preferences.UserComment.Buffer);
302
303 if (Ptr->Preferences.Reserved1.Buffer != NULL)
304 MIDL_user_free(Ptr->Preferences.Reserved1.Buffer);
305 break;
306
307 case UserLogonInformation:
308 if (Ptr->Logon.UserName.Buffer != NULL)
309 MIDL_user_free(Ptr->Logon.UserName.Buffer);
310
311 if (Ptr->Logon.FullName.Buffer != NULL)
312 MIDL_user_free(Ptr->Logon.FullName.Buffer);
313
314 if (Ptr->Logon.HomeDirectory.Buffer != NULL)
315 MIDL_user_free(Ptr->Logon.HomeDirectory.Buffer);
316
317 if (Ptr->Logon.HomeDirectoryDrive.Buffer != NULL)
318 MIDL_user_free(Ptr->Logon.HomeDirectoryDrive.Buffer);
319
320 if (Ptr->Logon.ScriptPath.Buffer != NULL)
321 MIDL_user_free(Ptr->Logon.ScriptPath.Buffer);
322
323 if (Ptr->Logon.ProfilePath.Buffer != NULL)
324 MIDL_user_free(Ptr->Logon.ProfilePath.Buffer);
325
326 if (Ptr->Logon.WorkStations.Buffer != NULL)
327 MIDL_user_free(Ptr->Logon.WorkStations.Buffer);
328
329 if (Ptr->Logon.LogonHours.LogonHours != NULL)
330 MIDL_user_free(Ptr->Logon.LogonHours.LogonHours);
331 break;
332
333 case UserLogonHoursInformation:
334 if (Ptr->LogonHours.LogonHours.LogonHours != NULL)
335 MIDL_user_free(Ptr->LogonHours.LogonHours.LogonHours);
336 break;
337
338 case UserAccountInformation:
339 if (Ptr->Account.UserName.Buffer != NULL)
340 MIDL_user_free(Ptr->Account.UserName.Buffer);
341
342 if (Ptr->Account.FullName.Buffer != NULL)
343 MIDL_user_free(Ptr->Account.FullName.Buffer);
344
345 if (Ptr->Account.HomeDirectory.Buffer != NULL)
346 MIDL_user_free(Ptr->Account.HomeDirectory.Buffer);
347
348 if (Ptr->Account.HomeDirectoryDrive.Buffer != NULL)
349 MIDL_user_free(Ptr->Account.HomeDirectoryDrive.Buffer);
350
351 if (Ptr->Account.ScriptPath.Buffer != NULL)
352 MIDL_user_free(Ptr->Account.ScriptPath.Buffer);
353
354 if (Ptr->Account.ProfilePath.Buffer != NULL)
355 MIDL_user_free(Ptr->Account.ProfilePath.Buffer);
356
357 if (Ptr->Account.AdminComment.Buffer != NULL)
358 MIDL_user_free(Ptr->Account.AdminComment.Buffer);
359
360 if (Ptr->Account.WorkStations.Buffer != NULL)
361 MIDL_user_free(Ptr->Account.WorkStations.Buffer);
362
363 if (Ptr->Account.LogonHours.LogonHours != NULL)
364 MIDL_user_free(Ptr->Account.LogonHours.LogonHours);
365 break;
366
367 case UserNameInformation:
368 if (Ptr->Name.UserName.Buffer != NULL)
369 MIDL_user_free(Ptr->Name.UserName.Buffer);
370
371 if (Ptr->Name.FullName.Buffer != NULL)
372 MIDL_user_free(Ptr->Name.FullName.Buffer);
373 break;
374
375 case UserAccountNameInformation:
376 if (Ptr->AccountName.UserName.Buffer != NULL)
377 MIDL_user_free(Ptr->AccountName.UserName.Buffer);
378 break;
379
380 case UserFullNameInformation:
381 if (Ptr->FullName.FullName.Buffer != NULL)
382 MIDL_user_free(Ptr->FullName.FullName.Buffer);
383 break;
384
385 case UserPrimaryGroupInformation:
386 break;
387
388 case UserHomeInformation:
389 if (Ptr->Home.HomeDirectory.Buffer != NULL)
390 MIDL_user_free(Ptr->Home.HomeDirectory.Buffer);
391
392 if (Ptr->Home.HomeDirectoryDrive.Buffer != NULL)
393 MIDL_user_free(Ptr->Home.HomeDirectoryDrive.Buffer);
394 break;
395
396 case UserScriptInformation:
397 if (Ptr->Script.ScriptPath.Buffer != NULL)
398 MIDL_user_free(Ptr->Script.ScriptPath.Buffer);
399
400 case UserProfileInformation:
401 if (Ptr->Profile.ProfilePath.Buffer != NULL)
402 MIDL_user_free(Ptr->Profile.ProfilePath.Buffer);
403
404 case UserAdminCommentInformation:
405 if (Ptr->AdminComment.AdminComment.Buffer != NULL)
406 MIDL_user_free(Ptr->AdminComment.AdminComment.Buffer);
407 break;
408
409 case UserWorkStationsInformation:
410 if (Ptr->WorkStations.WorkStations.Buffer != NULL)
411 MIDL_user_free(Ptr->WorkStations.WorkStations.Buffer);
412 break;
413
414 case UserSetPasswordInformation:
415 ERR("Information class UserSetPasswordInformation cannot be queried!\n");
416 break;
417
418 case UserControlInformation:
419 break;
420
421 case UserExpiresInformation:
422 break;
423
424 case UserInternal1Information:
425 break;
426
427 case UserInternal2Information:
428 break;
429
430 case UserParametersInformation:
431 if (Ptr->Parameters.Parameters.Buffer != NULL)
432 MIDL_user_free(Ptr->Parameters.Parameters.Buffer);
433 break;
434
435 case UserAllInformation:
436 if (Ptr->All.UserName.Buffer != NULL)
437 MIDL_user_free(Ptr->All.UserName.Buffer);
438
439 if (Ptr->All.FullName.Buffer != NULL)
440 MIDL_user_free(Ptr->All.FullName.Buffer);
441
442 if (Ptr->All.HomeDirectory.Buffer != NULL)
443 MIDL_user_free(Ptr->All.HomeDirectory.Buffer);
444
445 if (Ptr->All.HomeDirectoryDrive.Buffer != NULL)
446 MIDL_user_free(Ptr->All.HomeDirectoryDrive.Buffer);
447
448 if (Ptr->All.ScriptPath.Buffer != NULL)
449 MIDL_user_free(Ptr->All.ScriptPath.Buffer);
450
451 if (Ptr->All.ProfilePath.Buffer != NULL)
452 MIDL_user_free(Ptr->All.ProfilePath.Buffer);
453
454 if (Ptr->All.AdminComment.Buffer != NULL)
455 MIDL_user_free(Ptr->All.AdminComment.Buffer);
456
457 if (Ptr->All.WorkStations.Buffer != NULL)
458 MIDL_user_free(Ptr->All.WorkStations.Buffer);
459
460 if (Ptr->All.UserComment.Buffer != NULL)
461 MIDL_user_free(Ptr->All.UserComment.Buffer);
462
463 if (Ptr->All.Parameters.Buffer != NULL)
464 MIDL_user_free(Ptr->All.Parameters.Buffer);
465
466 if (Ptr->All.LmOwfPassword.Buffer != NULL)
467 MIDL_user_free(Ptr->All.LmOwfPassword.Buffer);
468
469 if (Ptr->All.NtOwfPassword.Buffer != NULL)
470 MIDL_user_free(Ptr->All.NtOwfPassword.Buffer);
471
472 if (Ptr->All.PrivateData.Buffer != NULL)
473 MIDL_user_free(Ptr->All.PrivateData.Buffer);
474
475 if (Ptr->All.SecurityDescriptor.SecurityDescriptor != NULL)
476 MIDL_user_free(Ptr->All.SecurityDescriptor.SecurityDescriptor);
477
478 if (Ptr->All.LogonHours.LogonHours != NULL)
479 MIDL_user_free(Ptr->All.LogonHours.LogonHours);
480 break;
481
482 default:
483 FIXME("Unsupported information class: %lu\n", InformationClass);
484 break;
485 }
486
487 MIDL_user_free(Ptr);
488 }
489
490 /* EOF */