[ADVAPI32]

Fix and EnumDependentServices[A/W]:
- If lpServices is NULL or cbBufSize is less than sizeof(ENUM_SERVICE_STATUS/W) pass a pointer to an internal status buffer to REnumDependentServicesA/W.

svn path=/trunk/; revision=53214
This commit is contained in:
Eric Kohl 2011-08-13 20:49:55 +00:00
parent d292220a34
commit fb59583ee0

View file

@ -744,18 +744,31 @@ EnumDependentServicesA(SC_HANDLE hService,
LPDWORD pcbBytesNeeded, LPDWORD pcbBytesNeeded,
LPDWORD lpServicesReturned) LPDWORD lpServicesReturned)
{ {
ENUM_SERVICE_STATUSA ServiceStatus;
LPENUM_SERVICE_STATUSA lpStatusPtr; LPENUM_SERVICE_STATUSA lpStatusPtr;
DWORD dwBufferSize;
DWORD dwError; DWORD dwError;
DWORD dwCount; DWORD dwCount;
TRACE("EnumServicesStatusA() called\n"); TRACE("EnumDependentServicesA() called\n");
if (lpServices == NULL || cbBufSize < sizeof(ENUM_SERVICE_STATUSA))
{
lpStatusPtr = &ServiceStatus;
dwBufferSize = sizeof(ENUM_SERVICE_STATUSA);
}
else
{
lpStatusPtr = lpServices;
dwBufferSize = cbBufSize;
}
RpcTryExcept RpcTryExcept
{ {
dwError = REnumDependentServicesA((SC_RPC_HANDLE)hService, dwError = REnumDependentServicesA((SC_RPC_HANDLE)hService,
dwServiceState, dwServiceState,
(LPBYTE)lpServices, (LPBYTE)lpStatusPtr,
cbBufSize, dwBufferSize,
pcbBytesNeeded, pcbBytesNeeded,
lpServicesReturned); lpServicesReturned);
} }
@ -767,18 +780,20 @@ EnumDependentServicesA(SC_HANDLE hService,
if (dwError == ERROR_SUCCESS || dwError == ERROR_MORE_DATA) if (dwError == ERROR_SUCCESS || dwError == ERROR_MORE_DATA)
{ {
lpStatusPtr = (LPENUM_SERVICE_STATUSA)lpServices; if (*lpServicesReturned > 0)
for (dwCount = 0; dwCount < *lpServicesReturned; dwCount++)
{ {
if (lpStatusPtr->lpServiceName) for (dwCount = 0; dwCount < *lpServicesReturned; dwCount++)
lpStatusPtr->lpServiceName = {
(LPSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpServiceName); if (lpStatusPtr->lpServiceName)
lpStatusPtr->lpServiceName =
(LPSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpServiceName);
if (lpStatusPtr->lpDisplayName) if (lpStatusPtr->lpDisplayName)
lpStatusPtr->lpDisplayName = lpStatusPtr->lpDisplayName =
(LPSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpDisplayName); (LPSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpDisplayName);
lpStatusPtr++; lpStatusPtr++;
}
} }
} }
@ -808,18 +823,31 @@ EnumDependentServicesW(SC_HANDLE hService,
LPDWORD pcbBytesNeeded, LPDWORD pcbBytesNeeded,
LPDWORD lpServicesReturned) LPDWORD lpServicesReturned)
{ {
ENUM_SERVICE_STATUSW ServiceStatus;
LPENUM_SERVICE_STATUSW lpStatusPtr; LPENUM_SERVICE_STATUSW lpStatusPtr;
DWORD dwBufferSize;
DWORD dwError; DWORD dwError;
DWORD dwCount; DWORD dwCount;
TRACE("EnumServicesStatusW() called\n"); TRACE("EnumDependentServicesW() called\n");
if (lpServices == NULL || cbBufSize < sizeof(ENUM_SERVICE_STATUSW))
{
lpStatusPtr = &ServiceStatus;
dwBufferSize = sizeof(ENUM_SERVICE_STATUSW);
}
else
{
lpStatusPtr = lpServices;
dwBufferSize = cbBufSize;
}
RpcTryExcept RpcTryExcept
{ {
dwError = REnumDependentServicesW((SC_RPC_HANDLE)hService, dwError = REnumDependentServicesW((SC_RPC_HANDLE)hService,
dwServiceState, dwServiceState,
(LPBYTE)lpServices, (LPBYTE)lpStatusPtr,
cbBufSize, dwBufferSize,
pcbBytesNeeded, pcbBytesNeeded,
lpServicesReturned); lpServicesReturned);
} }
@ -831,18 +859,20 @@ EnumDependentServicesW(SC_HANDLE hService,
if (dwError == ERROR_SUCCESS || dwError == ERROR_MORE_DATA) if (dwError == ERROR_SUCCESS || dwError == ERROR_MORE_DATA)
{ {
lpStatusPtr = (LPENUM_SERVICE_STATUSW)lpServices; if (*lpServicesReturned > 0)
for (dwCount = 0; dwCount < *lpServicesReturned; dwCount++)
{ {
if (lpStatusPtr->lpServiceName) for (dwCount = 0; dwCount < *lpServicesReturned; dwCount++)
lpStatusPtr->lpServiceName = {
(LPWSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpServiceName); if (lpStatusPtr->lpServiceName)
lpStatusPtr->lpServiceName =
(LPWSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpServiceName);
if (lpStatusPtr->lpDisplayName) if (lpStatusPtr->lpDisplayName)
lpStatusPtr->lpDisplayName = lpStatusPtr->lpDisplayName =
(LPWSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpDisplayName); (LPWSTR)((ULONG_PTR)lpServices + (ULONG_PTR)lpStatusPtr->lpDisplayName);
lpStatusPtr++; lpStatusPtr++;
}
} }
} }