[SAMSRV]
[reactos.git] / reactos / dll / win32 / samsrv / setup.c
1 /*
2 * COPYRIGHT: See COPYING in the top level directory
3 * PROJECT: Security Account Manager (SAM) Server
4 * FILE: reactos/dll/win32/samsrv/setup.c
5 * PURPOSE: Registry setup routines
6 *
7 * PROGRAMMERS: Eric Kohl
8 */
9
10 /* INCLUDES ****************************************************************/
11
12 #include "samsrv.h"
13
14 WINE_DEFAULT_DEBUG_CHANNEL(samsrv);
15
16
17 /* GLOBALS *****************************************************************/
18
19 #define TICKS_PER_SECOND 10000000LL
20
21 SID_IDENTIFIER_AUTHORITY SecurityNtAuthority = {SECURITY_NT_AUTHORITY};
22
23
24 /* FUNCTIONS ***************************************************************/
25
26 static BOOL
27 SampSetupAddMemberToAlias(HKEY hDomainKey,
28 ULONG AliasId,
29 PSID MemberSid)
30 {
31 DWORD dwDisposition;
32 LPWSTR MemberSidString = NULL;
33 WCHAR szKeyName[256];
34 HKEY hMembersKey;
35
36 ConvertSidToStringSidW(MemberSid, &MemberSidString);
37
38 swprintf(szKeyName, L"Aliases\\%08lX\\Members", AliasId);
39
40 if (!RegCreateKeyExW(hDomainKey,
41 szKeyName,
42 0,
43 NULL,
44 REG_OPTION_NON_VOLATILE,
45 KEY_ALL_ACCESS,
46 NULL,
47 &hMembersKey,
48 &dwDisposition))
49 {
50 RegSetValueEx(hMembersKey,
51 MemberSidString,
52 0,
53 REG_BINARY,
54 (LPVOID)MemberSid,
55 RtlLengthSid(MemberSid));
56
57 RegCloseKey(hMembersKey);
58 }
59
60 swprintf(szKeyName, L"Aliases\\Members\\%s", MemberSidString);
61
62 if (!RegCreateKeyExW(hDomainKey,
63 szKeyName,
64 0,
65 NULL,
66 REG_OPTION_NON_VOLATILE,
67 KEY_ALL_ACCESS,
68 NULL,
69 &hMembersKey,
70 &dwDisposition))
71 {
72 swprintf(szKeyName, L"%08lX", AliasId);
73
74 RegSetValueEx(hMembersKey,
75 szKeyName,
76 0,
77 REG_BINARY,
78 (LPVOID)MemberSid,
79 RtlLengthSid(MemberSid));
80
81 RegCloseKey(hMembersKey);
82 }
83
84 if (MemberSidString != NULL)
85 LocalFree(MemberSidString);
86
87 return TRUE;
88 }
89
90
91 static
92 NTSTATUS
93 SampSetupCreateAliasAccount(HANDLE hDomainKey,
94 LPCWSTR lpAccountName,
95 LPCWSTR lpDescription,
96 ULONG ulRelativeId)
97 {
98 WCHAR szAccountKeyName[32];
99 HANDLE hAccountKey = NULL;
100 HANDLE hNamesKey = NULL;
101 PSECURITY_DESCRIPTOR Sd = NULL;
102 ULONG SdSize = 0;
103 NTSTATUS Status;
104
105 swprintf(szAccountKeyName, L"Aliases\\%08lX", ulRelativeId);
106
107 Status = SampRegCreateKey(hDomainKey,
108 szAccountKeyName,
109 KEY_ALL_ACCESS,
110 &hAccountKey);
111 if (!NT_SUCCESS(Status))
112 return Status;
113
114 Status = SampRegSetValue(hAccountKey,
115 L"Name",
116 REG_SZ,
117 (LPVOID)lpAccountName,
118 (wcslen(lpAccountName) + 1) * sizeof(WCHAR));
119 if (!NT_SUCCESS(Status))
120 goto done;
121
122 Status = SampRegSetValue(hAccountKey,
123 L"Description",
124 REG_SZ,
125 (LPVOID)lpDescription,
126 (wcslen(lpDescription) + 1) * sizeof(WCHAR));
127 if (!NT_SUCCESS(Status))
128 goto done;
129
130 /* Create the server SD */
131 Status = SampCreateAliasSD(&Sd,
132 &SdSize);
133 if (!NT_SUCCESS(Status))
134 goto done;
135
136 /* Set SecDesc attribute*/
137 Status = SampRegSetValue(hAccountKey,
138 L"SecDesc",
139 REG_BINARY,
140 Sd,
141 SdSize);
142 if (!NT_SUCCESS(Status))
143 goto done;
144
145 Status = SampRegOpenKey(hDomainKey,
146 L"Aliases\\Names",
147 KEY_ALL_ACCESS,
148 &hNamesKey);
149 if (!NT_SUCCESS(Status))
150 goto done;
151
152 Status = SampRegSetValue(hNamesKey,
153 lpAccountName,
154 REG_DWORD,
155 (LPVOID)&ulRelativeId,
156 sizeof(ULONG));
157
158 done:
159 SampRegCloseKey(&hNamesKey);
160
161 if (Sd != NULL)
162 RtlFreeHeap(RtlGetProcessHeap(), 0, Sd);
163
164 if (hAccountKey != NULL)
165 {
166 SampRegCloseKey(&hAccountKey);
167
168 if (!NT_SUCCESS(Status))
169 SampRegDeleteKey(hDomainKey,
170 szAccountKeyName);
171 }
172
173 return Status;
174 }
175
176
177 static
178 NTSTATUS
179 SampSetupAddMemberToGroup(IN HANDLE hDomainKey,
180 IN ULONG GroupId,
181 IN ULONG MemberId)
182 {
183 WCHAR szKeyName[256];
184 HANDLE hGroupKey = NULL;
185 PULONG MembersBuffer = NULL;
186 ULONG MembersCount = 0;
187 ULONG Length = 0;
188 ULONG i;
189 NTSTATUS Status;
190
191 swprintf(szKeyName, L"Groups\\%08lX", GroupId);
192
193 Status = SampRegOpenKey(hDomainKey,
194 szKeyName,
195 KEY_ALL_ACCESS,
196 &hGroupKey);
197 if (!NT_SUCCESS(Status))
198 return Status;
199
200 Status = SampRegQueryValue(hGroupKey,
201 L"Members",
202 NULL,
203 NULL,
204 &Length);
205 if (!NT_SUCCESS(Status) && Status != STATUS_OBJECT_NAME_NOT_FOUND)
206 goto done;
207
208 MembersBuffer = midl_user_allocate(Length + sizeof(ULONG));
209 if (MembersBuffer == NULL)
210 {
211 Status = STATUS_INSUFFICIENT_RESOURCES;
212 goto done;
213 }
214
215 if (Status != STATUS_OBJECT_NAME_NOT_FOUND)
216 {
217 Status = SampRegQueryValue(hGroupKey,
218 L"Members",
219 NULL,
220 MembersBuffer,
221 &Length);
222 if (!NT_SUCCESS(Status))
223 goto done;
224
225 MembersCount = Length / sizeof(ULONG);
226 }
227
228 for (i = 0; i < MembersCount; i++)
229 {
230 if (MembersBuffer[i] == MemberId)
231 {
232 Status = STATUS_MEMBER_IN_GROUP;
233 goto done;
234 }
235 }
236
237 MembersBuffer[MembersCount] = MemberId;
238 Length += sizeof(ULONG);
239
240 Status = SampRegSetValue(hGroupKey,
241 L"Members",
242 REG_BINARY,
243 MembersBuffer,
244 Length);
245
246 done:
247 if (MembersBuffer != NULL)
248 midl_user_free(MembersBuffer);
249
250 SampRegCloseKey(&hGroupKey);
251
252 return Status;
253 }
254
255
256 static
257 NTSTATUS
258 SampSetupCreateGroupAccount(HANDLE hDomainKey,
259 LPCWSTR lpAccountName,
260 LPCWSTR lpComment,
261 ULONG ulRelativeId)
262 {
263 SAM_GROUP_FIXED_DATA FixedGroupData;
264 WCHAR szAccountKeyName[32];
265 HANDLE hAccountKey = NULL;
266 HANDLE hNamesKey = NULL;
267 PSECURITY_DESCRIPTOR Sd = NULL;
268 ULONG SdSize = 0;
269 NTSTATUS Status;
270
271 /* Initialize fixed group data */
272 FixedGroupData.Version = 1;
273 FixedGroupData.Reserved = 0;
274 FixedGroupData.GroupId = ulRelativeId;
275 FixedGroupData.Attributes = 0;
276
277 swprintf(szAccountKeyName, L"Groups\\%08lX", ulRelativeId);
278
279 Status = SampRegCreateKey(hDomainKey,
280 szAccountKeyName,
281 KEY_ALL_ACCESS,
282 &hAccountKey);
283 if (!NT_SUCCESS(Status))
284 return Status;
285
286 Status = SampRegSetValue(hAccountKey,
287 L"F",
288 REG_BINARY,
289 (LPVOID)&FixedGroupData,
290 sizeof(SAM_GROUP_FIXED_DATA));
291 if (!NT_SUCCESS(Status))
292 goto done;
293
294 Status = SampRegSetValue(hAccountKey,
295 L"Name",
296 REG_SZ,
297 (LPVOID)lpAccountName,
298 (wcslen(lpAccountName) + 1) * sizeof(WCHAR));
299 if (!NT_SUCCESS(Status))
300 goto done;
301
302 Status = SampRegSetValue(hAccountKey,
303 L"AdminComment",
304 REG_SZ,
305 (LPVOID)lpComment,
306 (wcslen(lpComment) + 1) * sizeof(WCHAR));
307 if (!NT_SUCCESS(Status))
308 goto done;
309
310 /* Create the security descriptor */
311 Status = SampCreateGroupSD(&Sd,
312 &SdSize);
313 if (!NT_SUCCESS(Status))
314 goto done;
315
316 /* Set the SecDesc attribute*/
317 Status = SampRegSetValue(hAccountKey,
318 L"SecDesc",
319 REG_BINARY,
320 Sd,
321 SdSize);
322 if (!NT_SUCCESS(Status))
323 goto done;
324
325 Status = SampRegOpenKey(hDomainKey,
326 L"Groups\\Names",
327 KEY_ALL_ACCESS,
328 &hNamesKey);
329 if (!NT_SUCCESS(Status))
330 goto done;
331
332 Status = SampRegSetValue(hNamesKey,
333 lpAccountName,
334 REG_DWORD,
335 (LPVOID)&ulRelativeId,
336 sizeof(ULONG));
337
338 done:
339 SampRegCloseKey(&hNamesKey);
340
341 if (Sd != NULL)
342 RtlFreeHeap(RtlGetProcessHeap(), 0, Sd);
343
344 if (hAccountKey != NULL)
345 {
346 SampRegCloseKey(&hAccountKey);
347
348 if (!NT_SUCCESS(Status))
349 SampRegDeleteKey(hDomainKey,
350 szAccountKeyName);
351 }
352
353 return Status;
354 }
355
356
357 static
358 NTSTATUS
359 SampSetupCreateUserAccount(HANDLE hDomainKey,
360 LPCWSTR lpAccountName,
361 LPCWSTR lpComment,
362 PSID lpDomainSid,
363 ULONG ulRelativeId,
364 ULONG UserAccountControl)
365 {
366 SAM_USER_FIXED_DATA FixedUserData;
367 GROUP_MEMBERSHIP GroupMembership;
368 UCHAR LogonHours[23];
369 LPWSTR lpEmptyString = L"";
370 WCHAR szAccountKeyName[32];
371 HANDLE hAccountKey = NULL;
372 HANDLE hNamesKey = NULL;
373 PSECURITY_DESCRIPTOR Sd = NULL;
374 ULONG SdSize = 0;
375 PSID UserSid = NULL;
376 NTSTATUS Status;
377
378 UserSid = AppendRidToSid(lpDomainSid,
379 ulRelativeId);
380
381 /* Create the security descriptor */
382 Status = SampCreateUserSD(UserSid,
383 &Sd,
384 &SdSize);
385 if (!NT_SUCCESS(Status))
386 goto done;
387
388 /* Initialize fixed user data */
389 FixedUserData.Version = 1;
390 FixedUserData.Reserved = 0;
391 FixedUserData.LastLogon.QuadPart = 0;
392 FixedUserData.LastLogoff.QuadPart = 0;
393 FixedUserData.PasswordLastSet.QuadPart = 0;
394 FixedUserData.AccountExpires.LowPart = MAXULONG;
395 FixedUserData.AccountExpires.HighPart = MAXLONG;
396 FixedUserData.LastBadPasswordTime.QuadPart = 0;
397 FixedUserData.UserId = ulRelativeId;
398 FixedUserData.PrimaryGroupId = DOMAIN_GROUP_RID_USERS;
399 FixedUserData.UserAccountControl = UserAccountControl;
400 FixedUserData.CountryCode = 0;
401 FixedUserData.CodePage = 0;
402 FixedUserData.BadPasswordCount = 0;
403 FixedUserData.LogonCount = 0;
404 FixedUserData.AdminCount = 0;
405 FixedUserData.OperatorCount = 0;
406
407 swprintf(szAccountKeyName, L"Users\\%08lX", ulRelativeId);
408
409 Status = SampRegCreateKey(hDomainKey,
410 szAccountKeyName,
411 KEY_ALL_ACCESS,
412 &hAccountKey);
413 if (!NT_SUCCESS(Status))
414 return Status;
415
416 Status = SampRegSetValue(hAccountKey,
417 L"F",
418 REG_BINARY,
419 (LPVOID)&FixedUserData,
420 sizeof(SAM_USER_FIXED_DATA));
421 if (!NT_SUCCESS(Status))
422 goto done;
423
424 Status = SampRegSetValue(hAccountKey,
425 L"Name",
426 REG_SZ,
427 (LPVOID)lpAccountName,
428 (wcslen(lpAccountName) + 1) * sizeof(WCHAR));
429 if (!NT_SUCCESS(Status))
430 goto done;
431
432 Status = SampRegSetValue(hAccountKey,
433 L"FullName",
434 REG_SZ,
435 (LPVOID)lpEmptyString,
436 sizeof(WCHAR));
437 if (!NT_SUCCESS(Status))
438 goto done;
439
440 Status = SampRegSetValue(hAccountKey,
441 L"HomeDirectory",
442 REG_SZ,
443 (LPVOID)lpEmptyString,
444 sizeof(WCHAR));
445 if (!NT_SUCCESS(Status))
446 goto done;
447
448 Status = SampRegSetValue(hAccountKey,
449 L"HomeDirectoryDrive",
450 REG_SZ,
451 (LPVOID)lpEmptyString,
452 sizeof(WCHAR));
453 if (!NT_SUCCESS(Status))
454 goto done;
455
456 Status = SampRegSetValue(hAccountKey,
457 L"ScriptPath",
458 REG_SZ,
459 (LPVOID)lpEmptyString,
460 sizeof(WCHAR));
461 if (!NT_SUCCESS(Status))
462 goto done;
463
464 Status = SampRegSetValue(hAccountKey,
465 L"ProfilePath",
466 REG_SZ,
467 (LPVOID)lpEmptyString,
468 sizeof(WCHAR));
469 if (!NT_SUCCESS(Status))
470 goto done;
471
472 Status = SampRegSetValue(hAccountKey,
473 L"AdminComment",
474 REG_SZ,
475 (LPVOID)lpComment,
476 (wcslen(lpComment) + 1) * sizeof(WCHAR));
477 if (!NT_SUCCESS(Status))
478 goto done;
479
480 Status = SampRegSetValue(hAccountKey,
481 L"UserComment",
482 REG_SZ,
483 (LPVOID)lpEmptyString,
484 sizeof(WCHAR));
485 if (!NT_SUCCESS(Status))
486 goto done;
487
488 Status = SampRegSetValue(hAccountKey,
489 L"WorkStations",
490 REG_SZ,
491 (LPVOID)lpEmptyString,
492 sizeof(WCHAR));
493 if (!NT_SUCCESS(Status))
494 goto done;
495
496 Status = SampRegSetValue(hAccountKey,
497 L"Parameters",
498 REG_SZ,
499 (LPVOID)lpEmptyString,
500 sizeof(WCHAR));
501 if (!NT_SUCCESS(Status))
502 goto done;
503
504 /* Set LogonHours attribute*/
505 *((PUSHORT)LogonHours) = 168;
506 memset(&(LogonHours[2]), 0xff, 21);
507
508 Status = SampRegSetValue(hAccountKey,
509 L"LogonHours",
510 REG_BINARY,
511 (LPVOID)LogonHours,
512 sizeof(LogonHours));
513 if (!NT_SUCCESS(Status))
514 goto done;
515
516 /* Set Groups attribute*/
517 GroupMembership.RelativeId = DOMAIN_GROUP_RID_USERS;
518 GroupMembership.Attributes = SE_GROUP_MANDATORY |
519 SE_GROUP_ENABLED |
520 SE_GROUP_ENABLED_BY_DEFAULT;
521
522 Status = SampRegSetValue(hAccountKey,
523 L"Groups",
524 REG_BINARY,
525 (LPVOID)&GroupMembership,
526 sizeof(GROUP_MEMBERSHIP));
527 if (!NT_SUCCESS(Status))
528 goto done;
529
530 /* Set LMPwd attribute*/
531 Status = SampRegSetValue(hAccountKey,
532 L"LMPwd",
533 REG_BINARY,
534 (LPVOID)&EmptyLmHash,
535 sizeof(ENCRYPTED_LM_OWF_PASSWORD));
536 if (!NT_SUCCESS(Status))
537 goto done;
538
539 /* Set NTPwd attribute*/
540 Status = SampRegSetValue(hAccountKey,
541 L"NTPwd",
542 REG_BINARY,
543 (LPVOID)&EmptyNtHash,
544 sizeof(ENCRYPTED_NT_OWF_PASSWORD));
545 if (!NT_SUCCESS(Status))
546 goto done;
547
548 /* Set LMPwdHistory attribute*/
549 Status = SampRegSetValue(hAccountKey,
550 L"LMPwdHistory",
551 REG_BINARY,
552 NULL,
553 0);
554 if (!NT_SUCCESS(Status))
555 goto done;
556
557 /* Set NTPwdHistory attribute*/
558 Status = SampRegSetValue(hAccountKey,
559 L"NTPwdHistory",
560 REG_BINARY,
561 NULL,
562 0);
563 if (!NT_SUCCESS(Status))
564 goto done;
565
566 /* Set PrivateData attribute*/
567 Status = SampRegSetValue(hAccountKey,
568 L"PrivateData",
569 REG_SZ,
570 (LPVOID)lpEmptyString,
571 sizeof(WCHAR));
572 if (!NT_SUCCESS(Status))
573 goto done;
574
575 /* Set the SecDesc attribute*/
576 Status = SampRegSetValue(hAccountKey,
577 L"SecDesc",
578 REG_BINARY,
579 Sd,
580 SdSize);
581 if (!NT_SUCCESS(Status))
582 goto done;
583
584 Status = SampRegOpenKey(hDomainKey,
585 L"Users\\Names",
586 KEY_ALL_ACCESS,
587 &hNamesKey);
588 if (!NT_SUCCESS(Status))
589 goto done;
590
591 Status = SampRegSetValue(hNamesKey,
592 lpAccountName,
593 REG_DWORD,
594 (LPVOID)&ulRelativeId,
595 sizeof(ULONG));
596
597 done:
598 SampRegCloseKey(&hNamesKey);
599
600 if (Sd != NULL)
601 RtlFreeHeap(RtlGetProcessHeap(), 0, Sd);
602
603 if (UserSid != NULL)
604 RtlFreeHeap(RtlGetProcessHeap(), 0, UserSid);
605
606 if (hAccountKey != NULL)
607 {
608 SampRegCloseKey(&hAccountKey);
609
610 if (!NT_SUCCESS(Status))
611 SampRegDeleteKey(hDomainKey,
612 szAccountKeyName);
613 }
614
615 return Status;
616 }
617
618
619 static
620 NTSTATUS
621 SampSetupCreateDomain(IN HANDLE hServerKey,
622 IN LPCWSTR lpKeyName,
623 IN LPCWSTR lpDomainName,
624 IN PSID lpDomainSid,
625 IN BOOLEAN bBuiltinDomain,
626 OUT HANDLE *lpDomainKey)
627 {
628 SAM_DOMAIN_FIXED_DATA FixedData;
629 WCHAR szDomainKeyName[32];
630 LPWSTR lpEmptyString = L"";
631 HANDLE hDomainKey = NULL;
632 HANDLE hAliasesKey = NULL;
633 HANDLE hGroupsKey = NULL;
634 HANDLE hUsersKey = NULL;
635 HANDLE hNamesKey = NULL;
636 PSECURITY_DESCRIPTOR Sd = NULL;
637 ULONG SdSize = 0;
638 NTSTATUS Status;
639
640 if (lpDomainKey != NULL)
641 *lpDomainKey = NULL;
642
643 /* Initialize the fixed domain data */
644 memset(&FixedData, 0, sizeof(SAM_DOMAIN_FIXED_DATA));
645 FixedData.Version = 1;
646 NtQuerySystemTime(&FixedData.CreationTime);
647 FixedData.DomainModifiedCount.QuadPart = 0;
648 FixedData.MaxPasswordAge.QuadPart = -(6LL * 7LL * 24LL * 60LL * 60LL * TICKS_PER_SECOND); /* 6 weeks */
649 FixedData.MinPasswordAge.QuadPart = 0; /* right now */
650 FixedData.ForceLogoff.QuadPart = LLONG_MAX; /* very far in the future aka never */
651 FixedData.LockoutDuration.QuadPart = -(30LL * 60LL * TICKS_PER_SECOND); /* 30 minutes */
652 FixedData.LockoutObservationWindow.QuadPart = -(30LL * 60LL * TICKS_PER_SECOND); /* 30 minutes */
653 FixedData.ModifiedCountAtLastPromotion.QuadPart = 0;
654 FixedData.NextRid = 1000;
655 FixedData.PasswordProperties = 0;
656 FixedData.MinPasswordLength = 0;
657 FixedData.PasswordHistoryLength = 0;
658 FixedData.LockoutThreshold = 0;
659 FixedData.DomainServerState = DomainServerEnabled;
660 FixedData.DomainServerRole = DomainServerRolePrimary;
661 FixedData.UasCompatibilityRequired = TRUE;
662
663 wcscpy(szDomainKeyName, L"Domains\\");
664 wcscat(szDomainKeyName, lpKeyName);
665
666 Status = SampRegCreateKey(hServerKey,
667 szDomainKeyName,
668 KEY_ALL_ACCESS,
669 &hDomainKey);
670 if (!NT_SUCCESS(Status))
671 return Status;
672
673 /* Set the fixed data value */
674 Status = SampRegSetValue(hDomainKey,
675 L"F",
676 REG_BINARY,
677 (LPVOID)&FixedData,
678 sizeof(SAM_DOMAIN_FIXED_DATA));
679 if (!NT_SUCCESS(Status))
680 goto done;
681
682 if (lpDomainSid != NULL)
683 {
684 Status = SampRegSetValue(hDomainKey,
685 L"Name",
686 REG_SZ,
687 (LPVOID)lpDomainName,
688 (wcslen(lpDomainName) + 1) * sizeof(WCHAR));
689 if (!NT_SUCCESS(Status))
690 goto done;
691
692 Status = SampRegSetValue(hDomainKey,
693 L"SID",
694 REG_BINARY,
695 (LPVOID)lpDomainSid,
696 RtlLengthSid(lpDomainSid));
697 if (!NT_SUCCESS(Status))
698 goto done;
699 }
700
701 Status = SampRegSetValue(hDomainKey,
702 L"OemInformation",
703 REG_SZ,
704 (LPVOID)lpEmptyString,
705 sizeof(WCHAR));
706 if (!NT_SUCCESS(Status))
707 goto done;
708
709 Status = SampRegSetValue(hDomainKey,
710 L"ReplicaSourceNodeName",
711 REG_SZ,
712 (LPVOID)lpEmptyString,
713 sizeof(WCHAR));
714 if (!NT_SUCCESS(Status))
715 goto done;
716
717 /* Create the Alias container */
718 Status = SampRegCreateKey(hDomainKey,
719 L"Aliases",
720 KEY_ALL_ACCESS,
721 &hAliasesKey);
722 if (!NT_SUCCESS(Status))
723 goto done;
724
725 Status = SampRegCreateKey(hAliasesKey,
726 L"Names",
727 KEY_ALL_ACCESS,
728 &hNamesKey);
729 if (!NT_SUCCESS(Status))
730 goto done;
731
732 SampRegCloseKey(&hNamesKey);
733
734 /* Create the Groups container */
735 Status = SampRegCreateKey(hDomainKey,
736 L"Groups",
737 KEY_ALL_ACCESS,
738 &hGroupsKey);
739 if (!NT_SUCCESS(Status))
740 goto done;
741
742 Status = SampRegCreateKey(hGroupsKey,
743 L"Names",
744 KEY_ALL_ACCESS,
745 &hNamesKey);
746 if (!NT_SUCCESS(Status))
747 goto done;
748
749 SampRegCloseKey(&hNamesKey);
750
751 /* Create the Users container */
752 Status = SampRegCreateKey(hDomainKey,
753 L"Users",
754 KEY_ALL_ACCESS,
755 &hUsersKey);
756 if (!NT_SUCCESS(Status))
757 goto done;
758
759 Status = SampRegCreateKey(hUsersKey,
760 L"Names",
761 KEY_ALL_ACCESS,
762 &hNamesKey);
763 if (!NT_SUCCESS(Status))
764 goto done;
765
766 /* Create the server SD */
767 if (bBuiltinDomain == TRUE)
768 Status = SampCreateBuiltinDomainSD(&Sd,
769 &SdSize);
770 else
771 Status = SampCreateAccountDomainSD(&Sd,
772 &SdSize);
773
774 if (!NT_SUCCESS(Status))
775 goto done;
776
777 /* Set SecDesc attribute*/
778 Status = SampRegSetValue(hServerKey,
779 L"SecDesc",
780 REG_BINARY,
781 Sd,
782 SdSize);
783 if (!NT_SUCCESS(Status))
784 goto done;
785
786 SampRegCloseKey(&hNamesKey);
787
788 if (lpDomainKey != NULL)
789 *lpDomainKey = hDomainKey;
790
791 done:
792 if (Sd != NULL)
793 RtlFreeHeap(RtlGetProcessHeap(), 0, Sd);
794
795 SampRegCloseKey(&hAliasesKey);
796 SampRegCloseKey(&hGroupsKey);
797 SampRegCloseKey(&hUsersKey);
798
799 if (!NT_SUCCESS(Status))
800 SampRegCloseKey(&hDomainKey);
801
802 return Status;
803 }
804
805
806 static
807 NTSTATUS
808 SampSetupCreateServer(IN HANDLE hSamKey,
809 OUT HANDLE *lpServerKey)
810 {
811 HANDLE hServerKey = NULL;
812 HANDLE hDomainsKey = NULL;
813 PSECURITY_DESCRIPTOR Sd = NULL;
814 ULONG SdSize = 0;
815 NTSTATUS Status;
816
817 Status = SampRegCreateKey(hSamKey,
818 L"SAM",
819 KEY_ALL_ACCESS,
820 &hServerKey);
821 if (!NT_SUCCESS(Status))
822 return Status;
823
824 Status = SampRegCreateKey(hServerKey,
825 L"Domains",
826 KEY_ALL_ACCESS,
827 &hDomainsKey);
828 if (!NT_SUCCESS(Status))
829 goto done;
830
831 /* Create the server SD */
832 Status = SampCreateServerSD(&Sd,
833 &SdSize);
834 if (!NT_SUCCESS(Status))
835 goto done;
836
837 /* Set SecDesc attribute*/
838 Status = SampRegSetValue(hServerKey,
839 L"SecDesc",
840 REG_BINARY,
841 Sd,
842 SdSize);
843 if (!NT_SUCCESS(Status))
844 goto done;
845
846 SampRegCloseKey(&hDomainsKey);
847
848 *lpServerKey = hServerKey;
849
850 done:
851 if (Sd != NULL)
852 RtlFreeHeap(RtlGetProcessHeap(), 0, Sd);
853
854 return Status;
855 }
856
857
858 NTSTATUS
859 SampGetAccountDomainInfo(PPOLICY_ACCOUNT_DOMAIN_INFO *AccountDomainInfo)
860 {
861 LSA_OBJECT_ATTRIBUTES ObjectAttributes;
862 LSA_HANDLE PolicyHandle;
863 NTSTATUS Status;
864
865 TRACE("SampGetAccountDomainInfo\n");
866
867 memset(&ObjectAttributes, 0, sizeof(LSA_OBJECT_ATTRIBUTES));
868 ObjectAttributes.Length = sizeof(LSA_OBJECT_ATTRIBUTES);
869
870 Status = LsaOpenPolicy(NULL,
871 &ObjectAttributes,
872 POLICY_VIEW_LOCAL_INFORMATION,
873 &PolicyHandle);
874 if (Status != STATUS_SUCCESS)
875 {
876 ERR("LsaOpenPolicy failed (Status: 0x%08lx)\n", Status);
877 return Status;
878 }
879
880 Status = LsaQueryInformationPolicy(PolicyHandle,
881 PolicyAccountDomainInformation,
882 (PVOID *)AccountDomainInfo);
883
884 LsaClose(PolicyHandle);
885
886 return Status;
887 }
888
889
890 BOOL
891 SampInitializeSAM(VOID)
892 {
893 PPOLICY_ACCOUNT_DOMAIN_INFO AccountDomainInfo = NULL;
894 HANDLE hSamKey = NULL;
895 HANDLE hServerKey = NULL;
896 HANDLE hBuiltinDomainKey = NULL;
897 HANDLE hAccountDomainKey = NULL;
898 PSID pBuiltinSid = NULL;
899 PSID pInteractiveSid = NULL;
900 PSID pAuthenticatedUserSid = NULL;
901 BOOL bResult = TRUE;
902 PSID pSid;
903 HINSTANCE hInstance;
904 WCHAR szComment[256];
905 WCHAR szName[80];
906 NTSTATUS Status;
907
908 TRACE("SampInitializeSAM() called\n");
909
910 hInstance = GetModuleHandleW(L"samsrv.dll");
911
912 /* Open the SAM key */
913 Status = SampRegOpenKey(NULL,
914 L"\\Registry\\Machine\\SAM",
915 KEY_READ | KEY_CREATE_SUB_KEY | KEY_ENUMERATE_SUB_KEYS,
916 &hSamKey);
917 if (!NT_SUCCESS(Status))
918 {
919 ERR("Failed to open the SAM key (Status: 0x%08lx)\n", Status);
920 return FALSE;
921 }
922
923 /* Create the SAM Server object */
924 Status = SampSetupCreateServer(hSamKey,
925 &hServerKey);
926 if (!NT_SUCCESS(Status))
927 {
928 bResult = FALSE;
929 goto done;
930 }
931
932 /* Create and initialize the Builtin Domain SID */
933 pBuiltinSid = RtlAllocateHeap(RtlGetProcessHeap(), 0, RtlLengthRequiredSid(1));
934 if (pBuiltinSid == NULL)
935 {
936 ERR("Failed to alloacte the Builtin Domain SID\n");
937 bResult = FALSE;
938 goto done;
939 }
940
941 RtlInitializeSid(pBuiltinSid, &SecurityNtAuthority, 1);
942 *(RtlSubAuthoritySid(pBuiltinSid, 0)) = SECURITY_BUILTIN_DOMAIN_RID;
943
944 /* Create and initialize the Interactive SID */
945 pInteractiveSid = RtlAllocateHeap(RtlGetProcessHeap(), 0, RtlLengthRequiredSid(1));
946 if (pInteractiveSid == NULL)
947 {
948 ERR("Failed to alloacte the Interactive SID\n");
949 bResult = FALSE;
950 goto done;
951 }
952
953 RtlInitializeSid(pInteractiveSid, &SecurityNtAuthority, 1);
954 *(RtlSubAuthoritySid(pInteractiveSid, 0)) = SECURITY_INTERACTIVE_RID;
955
956 /* Create and initialize the Authenticated User SID */
957 pAuthenticatedUserSid = RtlAllocateHeap(RtlGetProcessHeap(), 0, RtlLengthRequiredSid(1));
958 if (pAuthenticatedUserSid == NULL)
959 {
960 ERR("Failed to alloacte the Authenticated User SID\n");
961 bResult = FALSE;
962 goto done;
963 }
964
965 RtlInitializeSid(pAuthenticatedUserSid, &SecurityNtAuthority, 1);
966 *(RtlSubAuthoritySid(pAuthenticatedUserSid, 0)) = SECURITY_AUTHENTICATED_USER_RID;
967
968 /* Get account domain information */
969 Status = SampGetAccountDomainInfo(&AccountDomainInfo);
970 if (!NT_SUCCESS(Status))
971 {
972 ERR("SampGetAccountDomainInfo failed (Status %08lx)\n", Status);
973 bResult = FALSE;
974 goto done;
975 }
976
977 SampLoadString(hInstance, IDS_DOMAIN_BUILTIN_NAME, szName, 80);
978
979 /* Create the Builtin domain */
980 Status = SampSetupCreateDomain(hServerKey,
981 L"Builtin",
982 szName,
983 pBuiltinSid,
984 TRUE,
985 &hBuiltinDomainKey);
986 if (!NT_SUCCESS(Status))
987 {
988 bResult = FALSE;
989 goto done;
990 }
991
992 SampLoadString(hInstance, IDS_ALIAS_ADMINISTRATORS_NAME, szName, 80);
993 SampLoadString(hInstance, IDS_ALIAS_ADMINISTRATORS_COMMENT, szComment, 256);
994
995 SampSetupCreateAliasAccount(hBuiltinDomainKey,
996 szName,
997 szComment,
998 DOMAIN_ALIAS_RID_ADMINS);
999
1000 SampLoadString(hInstance, IDS_ALIAS_USERS_NAME, szName, 80);
1001 SampLoadString(hInstance, IDS_ALIAS_USERS_COMMENT, szComment, 256);
1002
1003 SampSetupCreateAliasAccount(hBuiltinDomainKey,
1004 szName,
1005 szComment,
1006 DOMAIN_ALIAS_RID_USERS);
1007
1008 SampLoadString(hInstance, IDS_ALIAS_GUESTS_NAME, szName, 80);
1009 SampLoadString(hInstance, IDS_ALIAS_GUESTS_COMMENT, szComment, 256);
1010
1011 SampSetupCreateAliasAccount(hBuiltinDomainKey,
1012 szName,
1013 szComment,
1014 DOMAIN_ALIAS_RID_GUESTS);
1015
1016 SampLoadString(hInstance, IDS_ALIAS_POWER_USERS_NAME, szName, 80);
1017 SampLoadString(hInstance, IDS_ALIAS_POWER_USERS_COMMENT, szComment, 256);
1018
1019 SampSetupCreateAliasAccount(hBuiltinDomainKey,
1020 szName,
1021 szComment,
1022 DOMAIN_ALIAS_RID_POWER_USERS);
1023
1024 /* Add the Administrator user to the Administrators alias */
1025 pSid = AppendRidToSid(AccountDomainInfo->DomainSid,
1026 DOMAIN_USER_RID_ADMIN);
1027 if (pSid != NULL)
1028 {
1029 SampSetupAddMemberToAlias(hBuiltinDomainKey,
1030 DOMAIN_ALIAS_RID_ADMINS,
1031 pSid);
1032
1033 RtlFreeHeap(RtlGetProcessHeap(), 0, pSid);
1034 }
1035
1036 /* Add the Guest user to the Guests alias */
1037 pSid = AppendRidToSid(AccountDomainInfo->DomainSid,
1038 DOMAIN_USER_RID_GUEST);
1039 if (pSid != NULL)
1040 {
1041 SampSetupAddMemberToAlias(hBuiltinDomainKey,
1042 DOMAIN_ALIAS_RID_GUESTS,
1043 pSid);
1044
1045 RtlFreeHeap(RtlGetProcessHeap(), 0, pSid);
1046 }
1047
1048 /* Add the Interactive SID to the Users alias */
1049 SampSetupAddMemberToAlias(hBuiltinDomainKey,
1050 DOMAIN_ALIAS_RID_USERS,
1051 pInteractiveSid);
1052
1053 /* Add the Authenticated User SID to the Users alias */
1054 SampSetupAddMemberToAlias(hBuiltinDomainKey,
1055 DOMAIN_ALIAS_RID_USERS,
1056 pAuthenticatedUserSid);
1057
1058 /* Create the Account domain */
1059 Status = SampSetupCreateDomain(hServerKey,
1060 L"Account",
1061 L"",
1062 AccountDomainInfo->DomainSid,
1063 FALSE,
1064 &hAccountDomainKey);
1065 if (!NT_SUCCESS(Status))
1066 {
1067 bResult = FALSE;
1068 goto done;
1069 }
1070
1071 SampLoadString(hInstance, IDS_GROUP_NONE_NAME, szName, 80);
1072 SampLoadString(hInstance, IDS_GROUP_NONE_COMMENT, szComment, 256);
1073
1074 SampSetupCreateGroupAccount(hAccountDomainKey,
1075 szName,
1076 szComment,
1077 DOMAIN_GROUP_RID_USERS);
1078
1079 SampLoadString(hInstance, IDS_USER_ADMINISTRATOR_NAME, szName, 80);
1080 SampLoadString(hInstance, IDS_USER_ADMINISTRATOR_COMMENT, szComment, 256);
1081
1082 SampSetupCreateUserAccount(hAccountDomainKey,
1083 szName,
1084 szComment,
1085 AccountDomainInfo->DomainSid,
1086 DOMAIN_USER_RID_ADMIN,
1087 USER_DONT_EXPIRE_PASSWORD | USER_NORMAL_ACCOUNT);
1088
1089 SampSetupAddMemberToGroup(hAccountDomainKey,
1090 DOMAIN_GROUP_RID_USERS,
1091 DOMAIN_USER_RID_ADMIN);
1092
1093 SampLoadString(hInstance, IDS_USER_GUEST_NAME, szName, 80);
1094 SampLoadString(hInstance, IDS_USER_GUEST_COMMENT, szComment, 256);
1095
1096 SampSetupCreateUserAccount(hAccountDomainKey,
1097 szName,
1098 szComment,
1099 AccountDomainInfo->DomainSid,
1100 DOMAIN_USER_RID_GUEST,
1101 USER_ACCOUNT_DISABLED | USER_DONT_EXPIRE_PASSWORD | USER_NORMAL_ACCOUNT);
1102
1103 SampSetupAddMemberToGroup(hAccountDomainKey,
1104 DOMAIN_GROUP_RID_USERS,
1105 DOMAIN_USER_RID_GUEST);
1106
1107 done:
1108 if (AccountDomainInfo)
1109 LsaFreeMemory(AccountDomainInfo);
1110
1111 if (pAuthenticatedUserSid)
1112 RtlFreeHeap(RtlGetProcessHeap(), 0, pAuthenticatedUserSid);
1113
1114 if (pInteractiveSid)
1115 RtlFreeHeap(RtlGetProcessHeap(), 0, pInteractiveSid);
1116
1117 if (pBuiltinSid)
1118 RtlFreeHeap(RtlGetProcessHeap(), 0, pBuiltinSid);
1119
1120 SampRegCloseKey(&hAccountDomainKey);
1121 SampRegCloseKey(&hBuiltinDomainKey);
1122 SampRegCloseKey(&hServerKey);
1123 SampRegCloseKey(&hSamKey);
1124
1125 TRACE("SampInitializeSAM() done\n");
1126
1127 return bResult;
1128 }