2 * Copyright 2006 Robert Reif
4 * netapi32 local group functions
6 * This library is free software; you can redistribute it and/or
7 * modify it under the terms of the GNU Lesser General Public
8 * License as published by the Free Software Foundation; either
9 * version 2.1 of the License, or (at your option) any later version.
11 * This library is distributed in the hope that it will be useful,
12 * but WITHOUT ANY WARRANTY; without even the implied warranty of
13 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
14 * Lesser General Public License for more details.
16 * You should have received a copy of the GNU Lesser General Public
17 * License along with this library; if not, write to the Free Software
18 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
23 WINE_DEFAULT_DEBUG_CHANNEL(netapi32
);
26 typedef enum _ENUM_PHASE
33 typedef struct _ENUM_CONTEXT
35 SAM_HANDLE ServerHandle
;
36 SAM_HANDLE DomainHandle
;
37 SAM_HANDLE BuiltinDomainHandle
;
38 SAM_HANDLE AccountDomainHandle
;
40 SAM_ENUMERATE_HANDLE EnumerationContext
;
41 PSAM_RID_ENUMERATION Buffer
;
46 } ENUM_CONTEXT
, *PENUM_CONTEXT
;
48 typedef struct _MEMBER_ENUM_CONTEXT
50 SAM_HANDLE ServerHandle
;
51 SAM_HANDLE DomainHandle
;
52 SAM_HANDLE AliasHandle
;
57 PLSA_REFERENCED_DOMAIN_LIST Domains
;
58 PLSA_TRANSLATED_NAME Names
;
60 } MEMBER_ENUM_CONTEXT
, *PMEMBER_ENUM_CONTEXT
;
65 BuildAliasInfoBuffer(PALIAS_GENERAL_INFORMATION AliasInfo
,
69 LPVOID LocalBuffer
= NULL
;
70 PLOCALGROUP_INFO_0 LocalInfo0
;
71 PLOCALGROUP_INFO_1 LocalInfo1
;
74 NET_API_STATUS ApiStatus
= NERR_Success
;
81 Size
= sizeof(LOCALGROUP_INFO_0
) +
82 AliasInfo
->Name
.Length
+ sizeof(WCHAR
);
86 Size
= sizeof(LOCALGROUP_INFO_1
) +
87 AliasInfo
->Name
.Length
+ sizeof(WCHAR
) +
88 AliasInfo
->AdminComment
.Length
+ sizeof(WCHAR
);
92 ApiStatus
= ERROR_INVALID_LEVEL
;
96 ApiStatus
= NetApiBufferAllocate(Size
, &LocalBuffer
);
97 if (ApiStatus
!= NERR_Success
)
100 ZeroMemory(LocalBuffer
, Size
);
105 LocalInfo0
= (PLOCALGROUP_INFO_0
)LocalBuffer
;
107 Ptr
= (LPWSTR
)LocalInfo0
++;
108 LocalInfo0
->lgrpi0_name
= Ptr
;
110 memcpy(LocalInfo0
->lgrpi0_name
,
111 AliasInfo
->Name
.Buffer
,
112 AliasInfo
->Name
.Length
);
113 LocalInfo0
->lgrpi0_name
[AliasInfo
->Name
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
117 LocalInfo1
= (PLOCALGROUP_INFO_1
)LocalBuffer
;
119 Ptr
= (LPWSTR
)((ULONG_PTR
)LocalInfo1
+ sizeof(LOCALGROUP_INFO_1
));
120 LocalInfo1
->lgrpi1_name
= Ptr
;
122 memcpy(LocalInfo1
->lgrpi1_name
,
123 AliasInfo
->Name
.Buffer
,
124 AliasInfo
->Name
.Length
);
125 LocalInfo1
->lgrpi1_name
[AliasInfo
->Name
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
127 Ptr
= (LPWSTR
)((ULONG_PTR
)Ptr
+ AliasInfo
->Name
.Length
+ sizeof(WCHAR
));
128 LocalInfo1
->lgrpi1_comment
= Ptr
;
130 memcpy(LocalInfo1
->lgrpi1_comment
,
131 AliasInfo
->AdminComment
.Buffer
,
132 AliasInfo
->AdminComment
.Length
);
133 LocalInfo1
->lgrpi1_comment
[AliasInfo
->AdminComment
.Length
/ sizeof(WCHAR
)] = UNICODE_NULL
;
138 if (ApiStatus
== NERR_Success
)
140 *Buffer
= LocalBuffer
;
144 if (LocalBuffer
!= NULL
)
145 NetApiBufferFree(LocalBuffer
);
154 FreeAliasInfo(PALIAS_GENERAL_INFORMATION AliasInfo
)
156 if (AliasInfo
->Name
.Buffer
!= NULL
)
157 SamFreeMemory(AliasInfo
->Name
.Buffer
);
159 if (AliasInfo
->AdminComment
.Buffer
!= NULL
)
160 SamFreeMemory(AliasInfo
->AdminComment
.Buffer
);
162 SamFreeMemory(AliasInfo
);
168 OpenAliasByName(SAM_HANDLE DomainHandle
,
169 PUNICODE_STRING AliasName
,
171 PSAM_HANDLE AliasHandle
)
173 PULONG RelativeIds
= NULL
;
174 PSID_NAME_USE Use
= NULL
;
175 NET_API_STATUS ApiStatus
= NERR_Success
;
176 NTSTATUS Status
= STATUS_SUCCESS
;
178 /* Get the RID for the given user name */
179 Status
= SamLookupNamesInDomain(DomainHandle
,
184 if (!NT_SUCCESS(Status
))
186 ERR("SamLookupNamesInDomain failed (Status %08lx)\n", Status
);
187 return NetpNtStatusToApiStatus(Status
);
190 /* Fail, if it is not an alias account */
191 if (Use
[0] != SidTypeAlias
)
193 ERR("Object is not an Alias!\n");
194 ApiStatus
= NERR_GroupNotFound
;
198 /* Open the alias account */
199 Status
= SamOpenAlias(DomainHandle
,
203 if (!NT_SUCCESS(Status
))
205 ERR("SamOpenDomain failed (Status %08lx)\n", Status
);
206 ApiStatus
= NetpNtStatusToApiStatus(Status
);
211 if (RelativeIds
!= NULL
)
212 SamFreeMemory(RelativeIds
);
223 BuildSidListFromDomainAndName(IN PUNICODE_STRING ServerName
,
224 IN PLOCALGROUP_MEMBERS_INFO_3 buf
,
226 OUT PLOCALGROUP_MEMBERS_INFO_0
*MemberList
)
228 OBJECT_ATTRIBUTES ObjectAttributes
;
229 LSA_HANDLE LsaHandle
= NULL
;
230 PUNICODE_STRING NamesArray
= NULL
;
232 PLSA_REFERENCED_DOMAIN_LIST Domains
= NULL
;
233 PLSA_TRANSLATED_SID Sids
= NULL
;
234 PLOCALGROUP_MEMBERS_INFO_0 MemberBuffer
= NULL
;
235 NET_API_STATUS ApiStatus
= NERR_Success
;
236 NTSTATUS Status
= STATUS_SUCCESS
;
238 ApiStatus
= NetApiBufferAllocate(sizeof(UNICODE_STRING
) * EntryCount
,
239 (LPVOID
*)&NamesArray
);
240 if (ApiStatus
!= NERR_Success
)
245 for (i
= 0; i
< EntryCount
; i
++)
247 RtlInitUnicodeString(&NamesArray
[i
],
248 buf
[i
].lgrmi3_domainandname
);
251 InitializeObjectAttributes(&ObjectAttributes
,
257 Status
= LsaOpenPolicy(ServerName
,
258 (PLSA_OBJECT_ATTRIBUTES
)&ObjectAttributes
,
261 if (!NT_SUCCESS(Status
))
263 ApiStatus
= NetpNtStatusToApiStatus(Status
);
267 Status
= LsaLookupNames(LsaHandle
,
272 if (!NT_SUCCESS(Status
))
274 ApiStatus
= NetpNtStatusToApiStatus(Status
);
278 ApiStatus
= NetApiBufferAllocate(sizeof(LOCALGROUP_MEMBERS_INFO_0
) * EntryCount
,
279 (LPVOID
*)&MemberBuffer
);
280 if (ApiStatus
!= NERR_Success
)
285 for (i
= 0; i
< EntryCount
; i
++)
287 ApiStatus
= BuildSidFromSidAndRid(Domains
->Domains
[Sids
[i
].DomainIndex
].Sid
,
289 &MemberBuffer
[i
].lgrmi0_sid
);
290 if (ApiStatus
!= NERR_Success
)
297 if (ApiStatus
!= NERR_Success
)
299 if (MemberBuffer
!= NULL
)
301 for (i
= 0; i
< EntryCount
; i
++)
303 if (MemberBuffer
[i
].lgrmi0_sid
!= NULL
)
304 NetApiBufferFree(MemberBuffer
[i
].lgrmi0_sid
);
307 NetApiBufferFree(MemberBuffer
);
316 LsaFreeMemory(Domains
);
318 if (LsaHandle
!= NULL
)
321 if (NamesArray
!= NULL
)
322 NetApiBufferFree(NamesArray
);
324 *MemberList
= MemberBuffer
;
330 /************************************************************
331 * NetLocalGroupAdd (NETAPI32.@)
341 ALIAS_ADM_COMMENT_INFORMATION AdminComment
;
342 UNICODE_STRING ServerName
;
343 UNICODE_STRING AliasName
;
344 SAM_HANDLE ServerHandle
= NULL
;
345 SAM_HANDLE DomainHandle
= NULL
;
346 SAM_HANDLE AliasHandle
= NULL
;
347 LPWSTR aliasname
= NULL
;
348 LPWSTR aliascomment
= NULL
;
350 NET_API_STATUS ApiStatus
= NERR_Success
;
351 NTSTATUS Status
= STATUS_SUCCESS
;
353 TRACE("(%s %d %p %p) stub!\n", debugstr_w(servername
), level
, buf
,
356 /* Initialize the Server name*/
357 if (servername
!= NULL
)
358 RtlInitUnicodeString(&ServerName
, servername
);
360 /* Initialize the Alias name*/
364 aliasname
= ((PLOCALGROUP_INFO_0
)buf
)->lgrpi0_name
;
369 aliasname
= ((PLOCALGROUP_INFO_1
)buf
)->lgrpi1_name
;
370 aliascomment
= ((PLOCALGROUP_INFO_1
)buf
)->lgrpi1_comment
;
374 return ERROR_INVALID_LEVEL
;
377 RtlInitUnicodeString(&AliasName
, aliasname
);
379 /* Connect to the SAM Server */
380 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
382 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
384 if (!NT_SUCCESS(Status
))
386 ERR("SamConnect failed (Status %08lx)\n", Status
);
387 ApiStatus
= NetpNtStatusToApiStatus(Status
);
391 /* Open the Builtin Domain */
392 Status
= OpenBuiltinDomain(ServerHandle
,
395 if (!NT_SUCCESS(Status
))
397 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
398 ApiStatus
= NetpNtStatusToApiStatus(Status
);
402 /* Try to open the Alias Account in the Builtin Domain */
403 ApiStatus
= OpenAliasByName(DomainHandle
,
405 ALIAS_READ_INFORMATION
,
407 if (ApiStatus
== NERR_Success
)
409 ERR("OpenAliasByName: alias %wZ already exists!\n", &AliasName
);
411 SamCloseHandle(AliasHandle
);
412 ApiStatus
= ERROR_ALIAS_EXISTS
;
416 ApiStatus
= NERR_Success
;
418 /* Close the Builtin Domain */
419 SamCloseHandle(DomainHandle
);
422 /* Open the account domain */
423 Status
= OpenAccountDomain(ServerHandle
,
424 (servername
!= NULL
) ? &ServerName
: NULL
,
425 DOMAIN_CREATE_ALIAS
| DOMAIN_LOOKUP
,
427 if (!NT_SUCCESS(Status
))
429 ERR("SamOpenDomain failed (Status %08lx)\n", Status
);
430 ApiStatus
= NetpNtStatusToApiStatus(Status
);
434 /* Create the alias */
435 Status
= SamCreateAliasInDomain(DomainHandle
,
437 DELETE
| ALIAS_WRITE_ACCOUNT
,
440 if (!NT_SUCCESS(Status
))
442 ERR("SamCreateAliasInDomain failed (Status %08lx)\n", Status
);
443 ApiStatus
= NetpNtStatusToApiStatus(Status
);
447 TRACE("Created alias \"%wZ\" (RID: %lu)\n", &AliasName
, RelativeId
);
449 /* Set the admin comment */
452 RtlInitUnicodeString(&AdminComment
.AdminComment
, aliascomment
);
454 Status
= SamSetInformationAlias(AliasHandle
,
455 AliasAdminCommentInformation
,
457 if (!NT_SUCCESS(Status
))
459 ERR("SamSetInformationAlias failed (Status %08lx)\n", Status
);
460 ApiStatus
= NetpNtStatusToApiStatus(Status
);
462 /* Delete the Alias if the Comment could not be set */
463 SamDeleteAlias(AliasHandle
);
470 if (AliasHandle
!= NULL
)
471 SamCloseHandle(AliasHandle
);
473 if (DomainHandle
!= NULL
)
474 SamCloseHandle(DomainHandle
);
476 if (ServerHandle
!= NULL
)
477 SamCloseHandle(ServerHandle
);
483 /************************************************************
484 * NetLocalGroupAddMember (NETAPI32.@)
488 NetLocalGroupAddMember(
493 LOCALGROUP_MEMBERS_INFO_0 Member
;
495 TRACE("(%s %s %p)\n", debugstr_w(servername
),
496 debugstr_w(groupname
), membersid
);
498 Member
.lgrmi0_sid
= membersid
;
500 return NetLocalGroupAddMembers(servername
,
508 /************************************************************
509 * NetLocalGroupAddMembers (NETAPI32.@)
513 NetLocalGroupAddMembers(
520 UNICODE_STRING ServerName
;
521 UNICODE_STRING AliasName
;
522 SAM_HANDLE ServerHandle
= NULL
;
523 SAM_HANDLE DomainHandle
= NULL
;
524 SAM_HANDLE AliasHandle
= NULL
;
525 PLOCALGROUP_MEMBERS_INFO_0 MemberList
= NULL
;
527 NET_API_STATUS ApiStatus
= NERR_Success
;
528 NTSTATUS Status
= STATUS_SUCCESS
;
530 TRACE("(%s %s %d %p %d)\n", debugstr_w(servername
),
531 debugstr_w(groupname
), level
, buf
, totalentries
);
533 if (servername
!= NULL
)
534 RtlInitUnicodeString(&ServerName
, servername
);
536 RtlInitUnicodeString(&AliasName
, groupname
);
541 MemberList
= (PLOCALGROUP_MEMBERS_INFO_0
)buf
;
545 Status
= BuildSidListFromDomainAndName((servername
!= NULL
) ? &ServerName
: NULL
,
546 (PLOCALGROUP_MEMBERS_INFO_3
)buf
,
549 if (!NT_SUCCESS(Status
))
551 ERR("BuildSidListFromDomainAndName failed (Status %08lx)\n", Status
);
552 ApiStatus
= NetpNtStatusToApiStatus(Status
);
558 ApiStatus
= ERROR_INVALID_LEVEL
;
562 /* Connect to the SAM Server */
563 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
565 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
567 if (!NT_SUCCESS(Status
))
569 ERR("SamConnect failed (Status %08lx)\n", Status
);
570 ApiStatus
= NetpNtStatusToApiStatus(Status
);
574 /* Open the Builtin Domain */
575 Status
= OpenBuiltinDomain(ServerHandle
,
578 if (!NT_SUCCESS(Status
))
580 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
581 ApiStatus
= NetpNtStatusToApiStatus(Status
);
585 /* Open the alias account in the builtin domain */
586 ApiStatus
= OpenAliasByName(DomainHandle
,
590 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
592 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
596 if (AliasHandle
== NULL
)
598 if (DomainHandle
!= NULL
)
599 SamCloseHandle(DomainHandle
);
601 /* Open the Acount Domain */
602 Status
= OpenAccountDomain(ServerHandle
,
603 (servername
!= NULL
) ? &ServerName
: NULL
,
606 if (!NT_SUCCESS(Status
))
608 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
609 ApiStatus
= NetpNtStatusToApiStatus(Status
);
613 /* Open the alias account in the account domain */
614 ApiStatus
= OpenAliasByName(DomainHandle
,
618 if (ApiStatus
!= NERR_Success
)
620 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
621 if (ApiStatus
== ERROR_NONE_MAPPED
)
622 ApiStatus
= NERR_GroupNotFound
;
627 /* Add new members to the alias */
628 for (i
= 0; i
< totalentries
; i
++)
630 Status
= SamAddMemberToAlias(AliasHandle
,
631 MemberList
[i
].lgrmi0_sid
);
632 if (!NT_SUCCESS(Status
))
634 ERR("SamAddMemberToAlias failed (Status %lu)\n", Status
);
635 ApiStatus
= NetpNtStatusToApiStatus(Status
);
641 if (level
== 3 && MemberList
!= NULL
)
643 for (i
= 0; i
< totalentries
; i
++)
645 if (MemberList
[i
].lgrmi0_sid
!= NULL
)
646 NetApiBufferFree(MemberList
[i
].lgrmi0_sid
);
649 NetApiBufferFree(MemberList
);
652 if (AliasHandle
!= NULL
)
653 SamCloseHandle(AliasHandle
);
655 if (DomainHandle
!= NULL
)
656 SamCloseHandle(DomainHandle
);
658 if (ServerHandle
!= NULL
)
659 SamCloseHandle(ServerHandle
);
665 /************************************************************
666 * NetLocalGroupDel (NETAPI32.@)
674 UNICODE_STRING ServerName
;
675 UNICODE_STRING GroupName
;
676 SAM_HANDLE ServerHandle
= NULL
;
677 SAM_HANDLE DomainHandle
= NULL
;
678 SAM_HANDLE AliasHandle
= NULL
;
679 NET_API_STATUS ApiStatus
= NERR_Success
;
680 NTSTATUS Status
= STATUS_SUCCESS
;
682 TRACE("(%s %s)\n", debugstr_w(servername
), debugstr_w(groupname
));
684 if (servername
!= NULL
)
685 RtlInitUnicodeString(&ServerName
, servername
);
687 RtlInitUnicodeString(&GroupName
, groupname
);
689 /* Connect to the SAM Server */
690 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
692 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
694 if (!NT_SUCCESS(Status
))
696 ERR("SamConnect failed (Status %08lx)\n", Status
);
697 ApiStatus
= NetpNtStatusToApiStatus(Status
);
701 /* Open the Builtin Domain */
702 Status
= OpenBuiltinDomain(ServerHandle
,
705 if (!NT_SUCCESS(Status
))
707 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
708 ApiStatus
= NetpNtStatusToApiStatus(Status
);
712 /* Open the alias account in the builtin domain */
713 ApiStatus
= OpenAliasByName(DomainHandle
,
717 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
719 TRACE("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
723 if (AliasHandle
== NULL
)
725 if (DomainHandle
!= NULL
)
727 SamCloseHandle(DomainHandle
);
731 /* Open the Acount Domain */
732 Status
= OpenAccountDomain(ServerHandle
,
733 (servername
!= NULL
) ? &ServerName
: NULL
,
736 if (!NT_SUCCESS(Status
))
738 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
739 ApiStatus
= NetpNtStatusToApiStatus(Status
);
743 /* Open the alias account in the account domain */
744 ApiStatus
= OpenAliasByName(DomainHandle
,
748 if (ApiStatus
!= NERR_Success
)
750 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
751 if (ApiStatus
== ERROR_NONE_MAPPED
)
752 ApiStatus
= NERR_GroupNotFound
;
757 /* Delete the alias */
758 Status
= SamDeleteAlias(AliasHandle
);
759 if (!NT_SUCCESS(Status
))
761 ERR("SamDeleteAlias failed (Status %08lx)\n", Status
);
762 ApiStatus
= NetpNtStatusToApiStatus(Status
);
767 if (AliasHandle
!= NULL
)
768 SamCloseHandle(AliasHandle
);
770 if (DomainHandle
!= NULL
)
771 SamCloseHandle(DomainHandle
);
773 if (ServerHandle
!= NULL
)
774 SamCloseHandle(ServerHandle
);
780 /************************************************************
781 * NetLocalGroupDelMember (NETAPI32.@)
785 NetLocalGroupDelMember(
790 LOCALGROUP_MEMBERS_INFO_0 Member
;
792 TRACE("(%s %s %p)\n", debugstr_w(servername
),
793 debugstr_w(groupname
), membersid
);
795 Member
.lgrmi0_sid
= membersid
;
797 return NetLocalGroupDelMembers(servername
,
805 /************************************************************
806 * NetLocalGroupDelMembers (NETAPI32.@)
810 NetLocalGroupDelMembers(
817 UNICODE_STRING ServerName
;
818 UNICODE_STRING AliasName
;
819 SAM_HANDLE ServerHandle
= NULL
;
820 SAM_HANDLE DomainHandle
= NULL
;
821 SAM_HANDLE AliasHandle
= NULL
;
822 PLOCALGROUP_MEMBERS_INFO_0 MemberList
= NULL
;
824 NET_API_STATUS ApiStatus
= NERR_Success
;
825 NTSTATUS Status
= STATUS_SUCCESS
;
827 TRACE("(%s %s %d %p %d)\n", debugstr_w(servername
),
828 debugstr_w(groupname
), level
, buf
, totalentries
);
830 if (servername
!= NULL
)
831 RtlInitUnicodeString(&ServerName
, servername
);
833 RtlInitUnicodeString(&AliasName
, groupname
);
838 MemberList
= (PLOCALGROUP_MEMBERS_INFO_0
)buf
;
842 Status
= BuildSidListFromDomainAndName((servername
!= NULL
) ? &ServerName
: NULL
,
843 (PLOCALGROUP_MEMBERS_INFO_3
)buf
,
846 if (!NT_SUCCESS(Status
))
848 ERR("BuildSidListFromDomainAndName failed (Status %08lx)\n", Status
);
849 ApiStatus
= NetpNtStatusToApiStatus(Status
);
855 ApiStatus
= ERROR_INVALID_LEVEL
;
859 /* Connect to the SAM Server */
860 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
862 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
864 if (!NT_SUCCESS(Status
))
866 ERR("SamConnect failed (Status %08lx)\n", Status
);
867 ApiStatus
= NetpNtStatusToApiStatus(Status
);
871 /* Open the Builtin Domain */
872 Status
= OpenBuiltinDomain(ServerHandle
,
875 if (!NT_SUCCESS(Status
))
877 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
878 ApiStatus
= NetpNtStatusToApiStatus(Status
);
882 /* Open the alias account in the builtin domain */
883 ApiStatus
= OpenAliasByName(DomainHandle
,
887 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
889 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
893 if (AliasHandle
== NULL
)
895 if (DomainHandle
!= NULL
)
896 SamCloseHandle(DomainHandle
);
898 /* Open the Acount Domain */
899 Status
= OpenAccountDomain(ServerHandle
,
900 (servername
!= NULL
) ? &ServerName
: NULL
,
903 if (!NT_SUCCESS(Status
))
905 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
906 ApiStatus
= NetpNtStatusToApiStatus(Status
);
910 /* Open the alias account in the account domain */
911 ApiStatus
= OpenAliasByName(DomainHandle
,
915 if (ApiStatus
!= NERR_Success
)
917 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
918 if (ApiStatus
== ERROR_NONE_MAPPED
)
919 ApiStatus
= NERR_GroupNotFound
;
924 /* Remove members from the alias */
925 for (i
= 0; i
< totalentries
; i
++)
927 Status
= SamRemoveMemberFromAlias(AliasHandle
,
928 MemberList
[i
].lgrmi0_sid
);
929 if (!NT_SUCCESS(Status
))
931 ERR("SamAddMemberToAlias failed (Status %lu)\n", Status
);
932 ApiStatus
= NetpNtStatusToApiStatus(Status
);
938 if (level
== 3 && MemberList
!= NULL
)
940 for (i
= 0; i
< totalentries
; i
++)
942 if (MemberList
[i
].lgrmi0_sid
!= NULL
)
943 NetApiBufferFree(MemberList
[i
].lgrmi0_sid
);
946 NetApiBufferFree(MemberList
);
949 if (AliasHandle
!= NULL
)
950 SamCloseHandle(AliasHandle
);
952 if (DomainHandle
!= NULL
)
953 SamCloseHandle(DomainHandle
);
955 if (ServerHandle
!= NULL
)
956 SamCloseHandle(ServerHandle
);
962 /************************************************************
963 * NetLocalGroupEnum (NETAPI32.@)
973 LPDWORD totalentries
,
974 PDWORD_PTR resumehandle
)
976 UNICODE_STRING ServerName
;
977 PSAM_RID_ENUMERATION CurrentAlias
;
978 PENUM_CONTEXT EnumContext
= NULL
;
980 SAM_HANDLE AliasHandle
= NULL
;
981 PALIAS_GENERAL_INFORMATION AliasInfo
= NULL
;
982 LPVOID Buffer
= NULL
;
983 NET_API_STATUS ApiStatus
= NERR_Success
;
984 NTSTATUS Status
= STATUS_SUCCESS
;
986 TRACE("(%s %d %p %d %p %p %p) stub!\n", debugstr_w(servername
),
987 level
, bufptr
, prefmaxlen
, entriesread
, totalentries
, resumehandle
);
993 if (servername
!= NULL
)
994 RtlInitUnicodeString(&ServerName
, servername
);
996 if (resumehandle
!= NULL
&& *resumehandle
!= 0)
998 EnumContext
= (PENUM_CONTEXT
)*resumehandle
;
1002 ApiStatus
= NetApiBufferAllocate(sizeof(ENUM_CONTEXT
), (PVOID
*)&EnumContext
);
1003 if (ApiStatus
!= NERR_Success
)
1006 EnumContext
->EnumerationContext
= 0;
1007 EnumContext
->Buffer
= NULL
;
1008 EnumContext
->Returned
= 0;
1009 EnumContext
->Index
= 0;
1011 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1012 &EnumContext
->ServerHandle
,
1013 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1015 if (!NT_SUCCESS(Status
))
1017 ERR("SamConnect failed (Status %08lx)\n", Status
);
1018 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1022 Status
= OpenAccountDomain(EnumContext
->ServerHandle
,
1023 (servername
!= NULL
) ? &ServerName
: NULL
,
1024 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
1025 &EnumContext
->AccountDomainHandle
);
1026 if (!NT_SUCCESS(Status
))
1028 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1029 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1033 Status
= OpenBuiltinDomain(EnumContext
->ServerHandle
,
1034 DOMAIN_LIST_ACCOUNTS
| DOMAIN_LOOKUP
,
1035 &EnumContext
->BuiltinDomainHandle
);
1036 if (!NT_SUCCESS(Status
))
1038 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1039 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1043 EnumContext
->Phase
= BuiltinPhase
;
1044 EnumContext
->DomainHandle
= EnumContext
->BuiltinDomainHandle
;
1050 TRACE("EnumContext->Index: %lu\n", EnumContext
->Index
);
1051 TRACE("EnumContext->Returned: %lu\n", EnumContext
->Returned
);
1053 if (EnumContext
->Index
>= EnumContext
->Returned
)
1055 TRACE("Calling SamEnumerateAliasesInDomain\n");
1057 Status
= SamEnumerateAliasesInDomain(EnumContext
->DomainHandle
,
1058 &EnumContext
->EnumerationContext
,
1059 (PVOID
*)&EnumContext
->Buffer
,
1061 &EnumContext
->Returned
);
1063 TRACE("SamEnumerateAliasesInDomain returned (Status %08lx)\n", Status
);
1064 if (!NT_SUCCESS(Status
))
1066 ERR("SamEnumerateAliasesInDomain failed (Status %08lx)\n", Status
);
1067 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1071 if (Status
== STATUS_MORE_ENTRIES
)
1073 ApiStatus
= NERR_BufTooSmall
;
1078 TRACE("EnumContext: %lu\n", EnumContext
);
1079 TRACE("EnumContext->Returned: %lu\n", EnumContext
->Returned
);
1080 TRACE("EnumContext->Buffer: %p\n", EnumContext
->Buffer
);
1082 /* Get a pointer to the current alias */
1083 CurrentAlias
= &EnumContext
->Buffer
[EnumContext
->Index
];
1085 TRACE("RID: %lu\n", CurrentAlias
->RelativeId
);
1087 Status
= SamOpenAlias(EnumContext
->DomainHandle
,
1088 ALIAS_READ_INFORMATION
,
1089 CurrentAlias
->RelativeId
,
1091 if (!NT_SUCCESS(Status
))
1093 ERR("SamOpenAlias failed (Status %08lx)\n", Status
);
1094 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1098 Status
= SamQueryInformationAlias(AliasHandle
,
1099 AliasGeneralInformation
,
1100 (PVOID
*)&AliasInfo
);
1101 if (!NT_SUCCESS(Status
))
1103 ERR("SamQueryInformationAlias failed (Status %08lx)\n", Status
);
1104 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1108 SamCloseHandle(AliasHandle
);
1111 TRACE("Name: %S\n", AliasInfo
->Name
.Buffer
);
1112 TRACE("Comment: %S\n", AliasInfo
->AdminComment
.Buffer
);
1114 ApiStatus
= BuildAliasInfoBuffer(AliasInfo
,
1117 if (ApiStatus
!= NERR_Success
)
1120 if (AliasInfo
!= NULL
)
1122 FreeAliasInfo(AliasInfo
);
1126 EnumContext
->Index
++;
1130 if (EnumContext
->Index
== EnumContext
->Returned
)
1132 switch (EnumContext
->Phase
)
1135 EnumContext
->Phase
= AccountPhase
;
1136 EnumContext
->DomainHandle
= EnumContext
->AccountDomainHandle
;
1137 EnumContext
->EnumerationContext
= 0;
1138 EnumContext
->Index
= 0;
1139 EnumContext
->Returned
= 0;
1141 if (EnumContext
->Buffer
!= NULL
)
1143 for (i
= 0; i
< EnumContext
->Returned
; i
++)
1145 SamFreeMemory(EnumContext
->Buffer
[i
].Name
.Buffer
);
1148 SamFreeMemory(EnumContext
->Buffer
);
1149 EnumContext
->Buffer
= NULL
;
1155 EnumContext
->Phase
= DonePhase
;
1162 if (ApiStatus
== NERR_Success
&& EnumContext
->Phase
!= DonePhase
)
1163 ApiStatus
= ERROR_MORE_DATA
;
1165 if (EnumContext
!= NULL
)
1166 *totalentries
= EnumContext
->Returned
;
1168 if (resumehandle
== NULL
|| ApiStatus
!= ERROR_MORE_DATA
)
1170 if (EnumContext
!= NULL
)
1172 if (EnumContext
->BuiltinDomainHandle
!= NULL
)
1173 SamCloseHandle(EnumContext
->BuiltinDomainHandle
);
1175 if (EnumContext
->AccountDomainHandle
!= NULL
)
1176 SamCloseHandle(EnumContext
->AccountDomainHandle
);
1178 if (EnumContext
->ServerHandle
!= NULL
)
1179 SamCloseHandle(EnumContext
->ServerHandle
);
1181 if (EnumContext
->Buffer
!= NULL
)
1183 for (i
= 0; i
< EnumContext
->Returned
; i
++)
1185 SamFreeMemory(EnumContext
->Buffer
[i
].Name
.Buffer
);
1188 SamFreeMemory(EnumContext
->Buffer
);
1191 NetApiBufferFree(EnumContext
);
1196 if (AliasHandle
!= NULL
)
1197 SamCloseHandle(AliasHandle
);
1199 if (AliasInfo
!= NULL
)
1200 FreeAliasInfo(AliasInfo
);
1202 if (resumehandle
!= NULL
)
1203 *resumehandle
= (DWORD_PTR
)EnumContext
;
1205 *bufptr
= (LPBYTE
)Buffer
;
1207 TRACE ("return %lu\n", ApiStatus
);
1213 /************************************************************
1214 * NetLocalGroupGetInfo (NETAPI32.@)
1218 NetLocalGroupGetInfo(
1224 UNICODE_STRING ServerName
;
1225 UNICODE_STRING GroupName
;
1226 SAM_HANDLE ServerHandle
= NULL
;
1227 SAM_HANDLE DomainHandle
= NULL
;
1228 SAM_HANDLE AliasHandle
= NULL
;
1229 PALIAS_GENERAL_INFORMATION AliasInfo
= NULL
;
1230 LPVOID Buffer
= NULL
;
1231 NET_API_STATUS ApiStatus
= NERR_Success
;
1232 NTSTATUS Status
= STATUS_SUCCESS
;
1234 TRACE("(%s %s %d %p) stub!\n", debugstr_w(servername
),
1235 debugstr_w(groupname
), level
, bufptr
);
1237 if (servername
!= NULL
)
1238 RtlInitUnicodeString(&ServerName
, servername
);
1240 RtlInitUnicodeString(&GroupName
, groupname
);
1242 /* Connect to the SAM Server */
1243 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1245 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1247 if (!NT_SUCCESS(Status
))
1249 ERR("SamConnect failed (Status %08lx)\n", Status
);
1250 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1254 /* Open the Builtin Domain */
1255 Status
= OpenBuiltinDomain(ServerHandle
,
1258 if (!NT_SUCCESS(Status
))
1260 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1261 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1265 /* Open the alias account in the builtin domain */
1266 ApiStatus
= OpenAliasByName(DomainHandle
,
1268 ALIAS_READ_INFORMATION
,
1270 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
1272 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
1276 if (AliasHandle
== NULL
)
1278 if (DomainHandle
!= NULL
)
1279 SamCloseHandle(DomainHandle
);
1281 /* Open the Acount Domain */
1282 Status
= OpenAccountDomain(ServerHandle
,
1283 (servername
!= NULL
) ? &ServerName
: NULL
,
1286 if (!NT_SUCCESS(Status
))
1288 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1289 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1293 /* Open the alias account in the account domain */
1294 ApiStatus
= OpenAliasByName(DomainHandle
,
1296 ALIAS_READ_INFORMATION
,
1298 if (ApiStatus
!= NERR_Success
)
1300 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
1301 if (ApiStatus
== ERROR_NONE_MAPPED
)
1302 ApiStatus
= NERR_GroupNotFound
;
1307 Status
= SamQueryInformationAlias(AliasHandle
,
1308 AliasGeneralInformation
,
1309 (PVOID
*)&AliasInfo
);
1310 if (!NT_SUCCESS(Status
))
1312 ERR("SamQueryInformationAlias failed (Status %08lx)\n", Status
);
1313 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1317 ApiStatus
= BuildAliasInfoBuffer(AliasInfo
,
1320 if (ApiStatus
!= NERR_Success
)
1324 if (AliasInfo
!= NULL
)
1325 FreeAliasInfo(AliasInfo
);
1327 if (AliasHandle
!= NULL
)
1328 SamCloseHandle(AliasHandle
);
1330 if (DomainHandle
!= NULL
)
1331 SamCloseHandle(DomainHandle
);
1333 if (ServerHandle
!= NULL
)
1334 SamCloseHandle(ServerHandle
);
1336 *bufptr
= (LPBYTE
)Buffer
;
1342 /************************************************************
1343 * NetLocalGroupGetMembers (NETAPI32.@)
1347 NetLocalGroupGetMembers(
1349 LPCWSTR localgroupname
,
1353 LPDWORD entriesread
,
1354 LPDWORD totalentries
,
1355 PDWORD_PTR resumehandle
)
1357 OBJECT_ATTRIBUTES ObjectAttributes
;
1358 UNICODE_STRING ServerName
;
1359 UNICODE_STRING AliasName
;
1360 PMEMBER_ENUM_CONTEXT EnumContext
= NULL
;
1361 LPVOID Buffer
= NULL
;
1362 PLOCALGROUP_MEMBERS_INFO_0 MembersInfo0
;
1363 PLOCALGROUP_MEMBERS_INFO_1 MembersInfo1
;
1364 PLOCALGROUP_MEMBERS_INFO_2 MembersInfo2
;
1365 PLOCALGROUP_MEMBERS_INFO_3 MembersInfo3
;
1370 NET_API_STATUS ApiStatus
= NERR_Success
;
1371 NTSTATUS Status
= STATUS_SUCCESS
;
1373 TRACE("(%s %s %d %p %d, %p %p %p)\n", debugstr_w(servername
),
1374 debugstr_w(localgroupname
), level
, bufptr
, prefmaxlen
, entriesread
,
1375 totalentries
, resumehandle
);
1381 if (servername
!= NULL
)
1382 RtlInitUnicodeString(&ServerName
, servername
);
1384 RtlInitUnicodeString(&AliasName
, localgroupname
);
1386 if (resumehandle
!= NULL
&& *resumehandle
!= 0)
1388 EnumContext
= (PMEMBER_ENUM_CONTEXT
)*resumehandle
;
1392 /* Allocate the enumeration context */
1393 ApiStatus
= NetApiBufferAllocate(sizeof(MEMBER_ENUM_CONTEXT
), (PVOID
*)&EnumContext
);
1394 if (ApiStatus
!= NERR_Success
)
1397 /* Connect to the SAM Server */
1398 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1399 &EnumContext
->ServerHandle
,
1400 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1402 if (!NT_SUCCESS(Status
))
1404 ERR("SamConnect failed (Status %08lx)\n", Status
);
1405 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1409 /* Open the Builtin Domain */
1410 Status
= OpenBuiltinDomain(EnumContext
->ServerHandle
,
1412 &EnumContext
->DomainHandle
);
1413 if (!NT_SUCCESS(Status
))
1415 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1416 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1420 /* Open the alias account in the builtin domain */
1421 ApiStatus
= OpenAliasByName(EnumContext
->DomainHandle
,
1424 &EnumContext
->AliasHandle
);
1425 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
1427 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
1431 if (EnumContext
->AliasHandle
== NULL
)
1433 if (EnumContext
->DomainHandle
!= NULL
)
1434 SamCloseHandle(EnumContext
->DomainHandle
);
1436 /* Open the Acount Domain */
1437 Status
= OpenAccountDomain(EnumContext
->ServerHandle
,
1438 (servername
!= NULL
) ? &ServerName
: NULL
,
1440 &EnumContext
->DomainHandle
);
1441 if (!NT_SUCCESS(Status
))
1443 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1444 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1448 /* Open the alias account in the account domain */
1449 ApiStatus
= OpenAliasByName(EnumContext
->DomainHandle
,
1452 &EnumContext
->AliasHandle
);
1453 if (ApiStatus
!= NERR_Success
)
1455 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
1456 if (ApiStatus
== ERROR_NONE_MAPPED
)
1457 ApiStatus
= NERR_GroupNotFound
;
1462 /* Get the member list */
1463 Status
= SamGetMembersInAlias(EnumContext
->AliasHandle
,
1465 &EnumContext
->Count
);
1466 if (!NT_SUCCESS(Status
))
1468 ERR("SamGetMemberInAlias failed (Status %08lx)\n", Status
);
1469 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1473 if (EnumContext
->Count
== 0)
1475 TRACE("No member found. We're done.\n");
1476 ApiStatus
= NERR_Success
;
1480 /* Get name and domain information for all members */
1483 InitializeObjectAttributes(&ObjectAttributes
,
1489 Status
= LsaOpenPolicy((servername
!= NULL
) ? &ServerName
: NULL
,
1490 (PLSA_OBJECT_ATTRIBUTES
)&ObjectAttributes
,
1492 &EnumContext
->LsaHandle
);
1493 if (!NT_SUCCESS(Status
))
1495 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1499 Status
= LsaLookupSids(EnumContext
->LsaHandle
,
1502 &EnumContext
->Domains
,
1503 &EnumContext
->Names
);
1504 if (!NT_SUCCESS(Status
))
1506 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1512 /* Calculate the required buffer size */
1513 for (i
= 0; i
< EnumContext
->Count
; i
++)
1518 Size
= sizeof(LOCALGROUP_MEMBERS_INFO_0
) +
1519 RtlLengthSid(EnumContext
->Sids
[i
]);
1523 Size
= sizeof(LOCALGROUP_MEMBERS_INFO_1
) +
1524 RtlLengthSid(EnumContext
->Sids
[i
]) +
1525 EnumContext
->Names
[i
].Name
.Length
+ sizeof(WCHAR
);
1529 Size
= sizeof(LOCALGROUP_MEMBERS_INFO_2
) +
1530 RtlLengthSid(EnumContext
->Sids
[i
]) +
1531 EnumContext
->Names
[i
].Name
.Length
+ sizeof(WCHAR
) +
1532 EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Length
+ sizeof(WCHAR
);
1536 Size
= sizeof(LOCALGROUP_MEMBERS_INFO_3
) +
1537 EnumContext
->Names
[i
].Name
.Length
+ sizeof(WCHAR
) +
1538 EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Length
+ sizeof(WCHAR
);
1542 ApiStatus
= ERROR_INVALID_LEVEL
;
1547 /* Allocate the member buffer */
1548 ApiStatus
= NetApiBufferAllocate(Size
, &Buffer
);
1549 if (ApiStatus
!= NERR_Success
)
1552 ZeroMemory(Buffer
, Size
);
1554 /* Fill the member buffer */
1558 MembersInfo0
= (PLOCALGROUP_MEMBERS_INFO_0
)Buffer
;
1559 Ptr
= (PVOID
)((ULONG_PTR
)Buffer
+ sizeof(LOCALGROUP_MEMBERS_INFO_0
) * EnumContext
->Count
);
1563 MembersInfo1
= (PLOCALGROUP_MEMBERS_INFO_1
)Buffer
;
1564 Ptr
= (PVOID
)((ULONG_PTR
)Buffer
+ sizeof(LOCALGROUP_MEMBERS_INFO_1
) * EnumContext
->Count
);
1568 MembersInfo2
= (PLOCALGROUP_MEMBERS_INFO_2
)Buffer
;
1569 Ptr
= (PVOID
)((ULONG_PTR
)Buffer
+ sizeof(LOCALGROUP_MEMBERS_INFO_2
) * EnumContext
->Count
);
1573 MembersInfo3
= (PLOCALGROUP_MEMBERS_INFO_3
)Buffer
;
1574 Ptr
= (PVOID
)((ULONG_PTR
)Buffer
+ sizeof(LOCALGROUP_MEMBERS_INFO_3
) * EnumContext
->Count
);
1578 for (i
= 0; i
< EnumContext
->Count
; i
++)
1583 MembersInfo0
->lgrmi0_sid
= (PSID
)Ptr
;
1585 SidLength
= RtlLengthSid(EnumContext
->Sids
[i
]);
1586 memcpy(MembersInfo0
->lgrmi0_sid
,
1587 EnumContext
->Sids
[i
],
1589 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ SidLength
);
1593 MembersInfo1
->lgrmi1_sid
= (PSID
)Ptr
;
1595 SidLength
= RtlLengthSid(EnumContext
->Sids
[i
]);
1596 memcpy(MembersInfo1
->lgrmi1_sid
,
1597 EnumContext
->Sids
[i
],
1600 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ SidLength
);
1602 MembersInfo1
->lgrmi1_sidusage
= EnumContext
->Names
[i
].Use
;
1604 TRACE("Name: %S\n", EnumContext
->Names
[i
].Name
.Buffer
);
1606 MembersInfo1
->lgrmi1_name
= (LPWSTR
)Ptr
;
1608 memcpy(MembersInfo1
->lgrmi1_name
,
1609 EnumContext
->Names
[i
].Name
.Buffer
,
1610 EnumContext
->Names
[i
].Name
.Length
);
1614 MembersInfo2
->lgrmi2_sid
= (PSID
)Ptr
;
1616 SidLength
= RtlLengthSid(EnumContext
->Sids
[i
]);
1617 memcpy(MembersInfo2
->lgrmi2_sid
,
1618 EnumContext
->Sids
[i
],
1621 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ SidLength
);
1623 MembersInfo2
->lgrmi2_sidusage
= EnumContext
->Names
[i
].Use
;
1625 MembersInfo2
->lgrmi2_domainandname
= (LPWSTR
)Ptr
;
1626 memcpy(MembersInfo2
->lgrmi2_domainandname
,
1627 EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Buffer
,
1628 EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Length
);
1630 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Length
);
1632 *((LPWSTR
)Ptr
) = L
'\\';
1634 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ sizeof(WCHAR
));
1637 EnumContext
->Names
[i
].Name
.Buffer
,
1638 EnumContext
->Names
[i
].Name
.Length
);
1642 MembersInfo3
->lgrmi3_domainandname
= (PSID
)Ptr
;
1643 memcpy(MembersInfo2
->lgrmi2_domainandname
,
1644 EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Buffer
,
1645 EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Length
);
1647 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ EnumContext
->Domains
->Domains
[EnumContext
->Names
[i
].DomainIndex
].Name
.Length
);
1649 *((LPWSTR
)Ptr
) = L
'\\';
1651 Ptr
= (PVOID
)((ULONG_PTR
)Ptr
+ sizeof(WCHAR
));
1654 EnumContext
->Names
[i
].Name
.Buffer
,
1655 EnumContext
->Names
[i
].Name
.Length
);
1660 *entriesread
= EnumContext
->Count
;
1662 *bufptr
= (LPBYTE
)Buffer
;
1665 if (EnumContext
!= NULL
)
1666 *totalentries
= EnumContext
->Count
;
1668 if (resumehandle
== NULL
|| ApiStatus
!= ERROR_MORE_DATA
)
1670 /* Release the enumeration context */
1671 if (EnumContext
!= NULL
)
1673 if (EnumContext
->LsaHandle
!= NULL
)
1674 LsaClose(EnumContext
->LsaHandle
);
1676 if (EnumContext
->AliasHandle
!= NULL
)
1677 SamCloseHandle(EnumContext
->AliasHandle
);
1679 if (EnumContext
->DomainHandle
!= NULL
)
1680 SamCloseHandle(EnumContext
->DomainHandle
);
1682 if (EnumContext
->ServerHandle
!= NULL
)
1683 SamCloseHandle(EnumContext
->ServerHandle
);
1685 if (EnumContext
->Sids
!= NULL
)
1686 SamFreeMemory(EnumContext
->Sids
);
1688 if (EnumContext
->Domains
!= NULL
)
1689 LsaFreeMemory(EnumContext
->Domains
);
1691 if (EnumContext
->Names
!= NULL
)
1692 LsaFreeMemory(EnumContext
->Names
);
1694 NetApiBufferFree(EnumContext
);
1703 /************************************************************
1704 * NetLocalGroupSetInfo (NETAPI32.@)
1708 NetLocalGroupSetInfo(
1715 UNICODE_STRING ServerName
;
1716 UNICODE_STRING AliasName
;
1717 SAM_HANDLE ServerHandle
= NULL
;
1718 SAM_HANDLE DomainHandle
= NULL
;
1719 SAM_HANDLE AliasHandle
= NULL
;
1720 ALIAS_NAME_INFORMATION AliasNameInfo
;
1721 ALIAS_ADM_COMMENT_INFORMATION AdminCommentInfo
;
1722 NET_API_STATUS ApiStatus
= NERR_Success
;
1723 NTSTATUS Status
= STATUS_SUCCESS
;
1725 TRACE("(%s %s %d %p %p)\n", debugstr_w(servername
),
1726 debugstr_w(groupname
), level
, buf
, parm_err
);
1728 if (parm_err
!= NULL
)
1729 *parm_err
= PARM_ERROR_NONE
;
1731 if (servername
!= NULL
)
1732 RtlInitUnicodeString(&ServerName
, servername
);
1734 RtlInitUnicodeString(&AliasName
, groupname
);
1736 /* Connect to the SAM Server */
1737 Status
= SamConnect((servername
!= NULL
) ? &ServerName
: NULL
,
1739 SAM_SERVER_CONNECT
| SAM_SERVER_LOOKUP_DOMAIN
,
1741 if (!NT_SUCCESS(Status
))
1743 ERR("SamConnect failed (Status %08lx)\n", Status
);
1744 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1748 /* Open the Builtin Domain */
1749 Status
= OpenBuiltinDomain(ServerHandle
,
1752 if (!NT_SUCCESS(Status
))
1754 ERR("OpenBuiltinDomain failed (Status %08lx)\n", Status
);
1755 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1759 /* Open the alias account in the builtin domain */
1760 ApiStatus
= OpenAliasByName(DomainHandle
,
1762 ALIAS_WRITE_ACCOUNT
,
1764 if (ApiStatus
!= NERR_Success
&& ApiStatus
!= ERROR_NONE_MAPPED
)
1766 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
1770 if (AliasHandle
== NULL
)
1772 if (DomainHandle
!= NULL
)
1773 SamCloseHandle(DomainHandle
);
1775 /* Open the Acount Domain */
1776 Status
= OpenAccountDomain(ServerHandle
,
1777 (servername
!= NULL
) ? &ServerName
: NULL
,
1780 if (!NT_SUCCESS(Status
))
1782 ERR("OpenAccountDomain failed (Status %08lx)\n", Status
);
1783 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1787 /* Open the alias account in the account domain */
1788 ApiStatus
= OpenAliasByName(DomainHandle
,
1790 ALIAS_WRITE_ACCOUNT
,
1792 if (ApiStatus
!= NERR_Success
)
1794 ERR("OpenAliasByName failed (ApiStatus %lu)\n", ApiStatus
);
1795 if (ApiStatus
== ERROR_NONE_MAPPED
)
1796 ApiStatus
= NERR_GroupNotFound
;
1804 /* Set the alias name */
1805 RtlInitUnicodeString(&AliasNameInfo
.Name
,
1806 ((PLOCALGROUP_INFO_0
)buf
)->lgrpi0_name
);
1808 Status
= SamSetInformationAlias(AliasHandle
,
1809 AliasNameInformation
,
1811 if (!NT_SUCCESS(Status
))
1813 TRACE("SamSetInformationAlias failed (ApiStatus %lu)\n", ApiStatus
);
1814 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1821 /* Set the alias admin comment */
1823 RtlInitUnicodeString(&AdminCommentInfo
.AdminComment
,
1824 ((PLOCALGROUP_INFO_1
)buf
)->lgrpi1_comment
);
1826 RtlInitUnicodeString(&AdminCommentInfo
.AdminComment
,
1827 ((PLOCALGROUP_INFO_1002
)buf
)->lgrpi1002_comment
);
1829 Status
= SamSetInformationAlias(AliasHandle
,
1830 AliasAdminCommentInformation
,
1832 if (!NT_SUCCESS(Status
))
1834 TRACE("SamSetInformationAlias failed (ApiStatus %lu)\n", ApiStatus
);
1835 ApiStatus
= NetpNtStatusToApiStatus(Status
);
1841 ApiStatus
= ERROR_INVALID_LEVEL
;
1846 if (AliasHandle
!= NULL
)
1847 SamCloseHandle(AliasHandle
);
1849 if (DomainHandle
!= NULL
)
1850 SamCloseHandle(DomainHandle
);
1852 if (ServerHandle
!= NULL
)
1853 SamCloseHandle(ServerHandle
);
1859 /************************************************************
1860 * NetLocalGroupSetMember (NETAPI32.@)
1862 NET_API_STATUS WINAPI
NetLocalGroupSetMembers(
1869 FIXME("(%s %s %d %p %d) stub!\n", debugstr_w(servername
),
1870 debugstr_w(groupname
), level
, buf
, totalentries
);
1871 return NERR_Success
;