Author: ekohl Date: Wed Nov 7 18:51:38 2012 New Revision: 57684
URL: http://svn.reactos.org/svn/reactos?rev=57684&view=rev Log: [NETAPI32] NetLocalGroupEnum: Make sure that built-in aliases are retrieved once and only one alias is enumerated upon each consecutive call. Retrieve name and comment for each alias.
Modified: trunk/reactos/dll/win32/netapi32/local_group.c
Modified: trunk/reactos/dll/win32/netapi32/local_group.c URL: http://svn.reactos.org/svn/reactos/trunk/reactos/dll/win32/netapi32/local_gr... ============================================================================== --- trunk/reactos/dll/win32/netapi32/local_group.c [iso-8859-1] (original) +++ trunk/reactos/dll/win32/netapi32/local_group.c [iso-8859-1] Wed Nov 7 18:51:38 2012 @@ -49,8 +49,10 @@ SAM_HANDLE AccountDomainHandle;
SAM_ENUMERATE_HANDLE EnumerationContext; - PSAM_RID_ENUMERATION EnumBuffer; - ULONG EnumReturned; + PSAM_RID_ENUMERATION Buffer; + ULONG Returned; + ULONG Index; + BOOLEAN BuiltinDone;
} ENUM_CONTEXT, *PENUM_CONTEXT;
@@ -241,9 +243,12 @@ LPDWORD totalentries, PDWORD_PTR resumehandle) { + PSAM_RID_ENUMERATION CurrentAlias; PENUM_CONTEXT EnumContext = NULL; PSID DomainSid = NULL; ULONG i; + SAM_HANDLE AliasHandle = NULL; + PALIAS_GENERAL_INFORMATION AliasInfo = NULL;
NET_API_STATUS ApiStatus = NERR_Success; NTSTATUS Status = STATUS_SUCCESS; @@ -267,8 +272,10 @@ goto done;
EnumContext->EnumerationContext = 0; - EnumContext->EnumBuffer = NULL; - EnumContext->EnumReturned = 0; + EnumContext->Buffer = NULL; + EnumContext->Returned = 0; + EnumContext->Index = 0; + EnumContext->BuiltinDone = FALSE;
Status = SamConnect(NULL, &EnumContext->ServerHandle, @@ -290,7 +297,7 @@ }
Status = SamOpenDomain(EnumContext->ServerHandle, - DOMAIN_LIST_ACCOUNTS, + DOMAIN_LIST_ACCOUNTS | DOMAIN_LOOKUP, DomainSid, &EnumContext->AccountDomainHandle);
@@ -312,7 +319,7 @@ }
Status = SamOpenDomain(EnumContext->ServerHandle, - DOMAIN_LIST_ACCOUNTS, + DOMAIN_LIST_ACCOUNTS | DOMAIN_LOOKUP, DomainSid, &EnumContext->BuiltinDomainHandle);
@@ -326,40 +333,96 @@ } }
+ while (TRUE) { - Status = SamEnumerateAliasesInDomain(EnumContext->BuiltinDomainHandle, - &EnumContext->EnumerationContext, - (PVOID *)&EnumContext->EnumBuffer, - prefmaxlen, - &EnumContext->EnumReturned); - - TRACE("SamEnumerateAliasesInDomain returned (Status %08lx)\n", Status); - - if (!NT_SUCCESS(Status)) - { - ERR("SamEnumerateAliasesInDomain failed (Status %08lx)\n", Status); - ApiStatus = NetpNtStatusToApiStatus(Status); - goto done; + + if (EnumContext->Index >= EnumContext->Returned) + { + if (EnumContext->BuiltinDone == TRUE) + { + ApiStatus = NERR_Success; + goto done; + } + + TRACE("Calling SamEnumerateAliasesInDomain\n"); + + Status = SamEnumerateAliasesInDomain(EnumContext->BuiltinDomainHandle, + &EnumContext->EnumerationContext, + (PVOID *)&EnumContext->Buffer, + prefmaxlen, + &EnumContext->Returned); + + TRACE("SamEnumerateAliasesInDomain returned (Status %08lx)\n", Status); + if (!NT_SUCCESS(Status)) + { + ERR("SamEnumerateAliasesInDomain failed (Status %08lx)\n", Status); + ApiStatus = NetpNtStatusToApiStatus(Status); + goto done; + } + + if (Status == STATUS_MORE_ENTRIES) + { + ApiStatus = NERR_BufTooSmall; + goto done; + } + else + { + EnumContext->BuiltinDone = TRUE; + } }
TRACE("EnumContext: %lu\n", EnumContext); - TRACE("EnumReturned: %lu\n", EnumContext->EnumReturned); - TRACE("EnumBuffer: %p\n", EnumContext->EnumBuffer); - - for (i = 0; i < EnumContext->EnumReturned; i++) - { - TRACE("RID: %lu\n", EnumContext->EnumBuffer[i].RelativeId); - TRACE("Name: %p\n", EnumContext->EnumBuffer[i].Name.Buffer); - TRACE("Name: %S\n", EnumContext->EnumBuffer[i].Name.Buffer); - if (EnumContext->EnumBuffer[i].Name.Buffer != NULL) - { - TRACE("Name: %hx\n", EnumContext->EnumBuffer[i].Name.Buffer[0]); - } - } - - if (Status != STATUS_MORE_ENTRIES) - break; + TRACE("EnumContext->Returned: %lu\n", EnumContext->Returned); + TRACE("EnumContext->Buffer: %p\n", EnumContext->Buffer); + + /* Get a pointer to the current alias */ + CurrentAlias = &EnumContext->Buffer[EnumContext->Index]; + + TRACE("RID: %lu\n", CurrentAlias->RelativeId); + + Status = SamOpenAlias(EnumContext->BuiltinDomainHandle, + ALIAS_READ_INFORMATION, + CurrentAlias->RelativeId, + &AliasHandle); + if (!NT_SUCCESS(Status)) + { + ERR("SamOpenAlias failed (Status %08lx)\n", Status); + ApiStatus = NetpNtStatusToApiStatus(Status); + goto done; + } + + Status = SamQueryInformationAlias(AliasHandle, + AliasGeneralInformation, + (PVOID *)&AliasInfo); + if (!NT_SUCCESS(Status)) + { + ERR("SamQueryInformationAlias failed (Status %08lx)\n", Status); + ApiStatus = NetpNtStatusToApiStatus(Status); + goto done; + } + + SamCloseHandle(AliasHandle); + AliasHandle = NULL; + + TRACE("Name: %S\n", AliasInfo->Name.Buffer); + TRACE("Comment: %S\n", AliasInfo->AdminComment.Buffer); + + + if (AliasInfo != NULL) + { + if (AliasInfo->Name.Buffer != NULL) + SamFreeMemory(AliasInfo->Name.Buffer); + + if (AliasInfo->AdminComment.Buffer != NULL) + SamFreeMemory(AliasInfo->AdminComment.Buffer); + + SamFreeMemory(AliasInfo); + AliasInfo = NULL; + } + + + EnumContext->Index++; }
@@ -377,14 +440,14 @@ if (EnumContext->ServerHandle != NULL) SamCloseHandle(EnumContext->ServerHandle);
- if (EnumContext->EnumBuffer != NULL) + if (EnumContext->Buffer != NULL) { - for (i = 0; i < EnumContext->EnumReturned; i++) + for (i = 0; i < EnumContext->Returned; i++) { - SamFreeMemory(EnumContext->EnumBuffer[i].Name.Buffer); + SamFreeMemory(EnumContext->Buffer[i].Name.Buffer); }
- SamFreeMemory(EnumContext->EnumBuffer); + SamFreeMemory(EnumContext->Buffer); }
NetApiBufferFree(EnumContext); @@ -392,6 +455,19 @@ } }
+ if (AliasHandle != NULL) + SamCloseHandle(AliasHandle); + + if (AliasInfo != NULL) + { + if (AliasInfo->Name.Buffer != NULL) + SamFreeMemory(AliasInfo->Name.Buffer); + + if (AliasInfo->AdminComment.Buffer != NULL) + SamFreeMemory(AliasInfo->AdminComment.Buffer); + + SamFreeMemory(AliasInfo); + }
if (resumehandle != NULL) *resumehandle = (DWORD_PTR)EnumContext;