https://git.reactos.org/?p=reactos.git;a=commitdiff;h=5da008c33837c03c1c1866...
commit 5da008c33837c03c1c186604aff1b6aec462bfb8 Author: Eric Kohl eric.kohl@reactos.org AuthorDate: Mon Dec 31 16:14:04 2018 +0100 Commit: Eric Kohl eric.kohl@reactos.org CommitDate: Mon Dec 31 16:15:16 2018 +0100
[UMPNPMGR] PNP_GetDeviceListSize: Implement the buffer size calculation for the enumeration of services instances. --- base/services/umpnpmgr/umpnpmgr.c | 116 +++++++++++++++++++++++++++++++++++++- 1 file changed, 115 insertions(+), 1 deletion(-)
diff --git a/base/services/umpnpmgr/umpnpmgr.c b/base/services/umpnpmgr/umpnpmgr.c index e7d1d42bdf..11911cbb11 100644 --- a/base/services/umpnpmgr/umpnpmgr.c +++ b/base/services/umpnpmgr/umpnpmgr.c @@ -580,6 +580,17 @@ GetRelationsInstanceList( }
+static +CONFIGRET +GetServiceInstanceList( + _In_ PWSTR pszService, + _Inout_ PWSTR pszBuffer, + _Inout_ PDWORD pulLength) +{ + return CR_CALL_NOT_IMPLEMENTED; +} + + static CONFIGRET GetDeviceInstanceList( @@ -810,6 +821,9 @@ PNP_GetDeviceList( } else if (ulFlags & CM_GETIDLIST_FILTER_SERVICE) { + ret = GetServiceInstanceList(pszFilter, + Buffer, + pulLength); ret = CR_CALL_NOT_IMPLEMENTED; } else if (ulFlags & CM_GETIDLIST_FILTER_ENUMERATOR) @@ -892,6 +906,105 @@ GetRelationsInstanceListSize( }
+static +CONFIGRET +GetServiceInstanceListSize( + _In_ PWSTR pszService, + _Out_ PDWORD pulLength) +{ + HKEY hServicesKey = NULL, hServiceKey = NULL, hEnumKey = NULL; + DWORD dwValues, dwMaxValueLength, dwSize; + DWORD dwError; + CONFIGRET ret = CR_SUCCESS; + + /* Open the device key */ + dwError = RegOpenKeyExW(HKEY_LOCAL_MACHINE, + L"System\CurrentControlSet\Services", + 0, + KEY_READ, + &hServicesKey); + if (dwError != ERROR_SUCCESS) + { + DPRINT("Failed to open the services key (Error %lu)\n", dwError); + return CR_REGISTRY_ERROR; + } + + dwError = RegOpenKeyExW(hServicesKey, + pszService, + 0, + KEY_READ, + &hServiceKey); + if (dwError != ERROR_SUCCESS) + { + DPRINT("Failed to open the service key (Error %lu)\n", dwError); + ret = CR_REGISTRY_ERROR; + goto Done; + } + + dwError = RegOpenKeyExW(hServiceKey, + L"Enum", + 0, + KEY_READ, + &hEnumKey); + if (dwError != ERROR_SUCCESS) + { + DPRINT("Failed to open the service enum key (Error %lu)\n", dwError); + ret = CR_REGISTRY_ERROR; + goto Done; + } + + /* Retrieve the number of device instances */ + dwSize = sizeof(DWORD); + dwError = RegQueryValueExW(hEnumKey, + L"Count", + NULL, + NULL, + (LPBYTE)&dwValues, + &dwSize); + if (dwError != ERROR_SUCCESS) + { + DPRINT("RegQueryValueExW failed (Error %lu)\n", dwError); + dwValues = 1; + } + + /* Retrieve the maximum instance name length */ + dwError = RegQueryInfoKeyW(hEnumKey, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + NULL, + &dwMaxValueLength, + NULL, + NULL); + if (dwError != ERROR_SUCCESS) + { + DPRINT("RegQueryInfoKeyW failed (Error %lu)\n", dwError); + dwMaxValueLength = MAX_DEVICE_ID_LEN; + } + + DPRINT("dwValues %lu dwMaxValueLength %lu\n", dwValues, dwMaxValueLength / sizeof(WCHAR)); + + /* Return the largest possible buffer size */ + *pulLength = dwValues * dwMaxValueLength / sizeof(WCHAR) + 2; + +Done: + if (hEnumKey != NULL) + RegCloseKey(hEnumKey); + + if (hServiceKey != NULL) + RegCloseKey(hServiceKey); + + if (hServicesKey != NULL) + RegCloseKey(hServicesKey); + + return ret; +} + + static CONFIGRET GetDeviceInstanceListSize( @@ -1080,7 +1193,8 @@ PNP_GetDeviceListSize( } else if (ulFlags & CM_GETIDLIST_FILTER_SERVICE) { - ret = CR_CALL_NOT_IMPLEMENTED; + ret = GetServiceInstanceListSize(pszFilter, + pulLength); } else if (ulFlags & CM_GETIDLIST_FILTER_ENUMERATOR) {