Module: wine Branch: master Commit: ee1706035aea9764efd80eef6ef764396c450439 URL: http://source.winehq.org/git/wine.git/?a=commit;h=ee1706035aea9764efd80eef6e...
Author: Alexandre Julliard julliard@winehq.org Date: Wed Feb 28 20:47:51 2007 +0100
advapi32: Reimplement QueryServiceConfigA on top of QueryServiceConfigW.
---
dlls/advapi32/service.c | 186 +++++++++++++---------------------------------- 1 files changed, 52 insertions(+), 134 deletions(-)
diff --git a/dlls/advapi32/service.c b/dlls/advapi32/service.c index 24b209e..9e482df 100644 --- a/dlls/advapi32/service.c +++ b/dlls/advapi32/service.c @@ -1644,146 +1644,64 @@ BOOL WINAPI QueryServiceStatusEx(SC_HANDLE hService, SC_STATUS_TYPE InfoLevel, /****************************************************************************** * QueryServiceConfigA [ADVAPI32.@] */ -BOOL WINAPI -QueryServiceConfigA( SC_HANDLE hService, - LPQUERY_SERVICE_CONFIGA lpServiceConfig, - DWORD cbBufSize, LPDWORD pcbBytesNeeded) +BOOL WINAPI QueryServiceConfigA( SC_HANDLE hService, LPQUERY_SERVICE_CONFIGA config, + DWORD size, LPDWORD needed ) { - static const CHAR szDisplayName[] = "DisplayName"; - static const CHAR szType[] = "Type"; - static const CHAR szStart[] = "Start"; - static const CHAR szError[] = "ErrorControl"; - static const CHAR szImagePath[] = "ImagePath"; - static const CHAR szGroup[] = "Group"; - static const CHAR szDependencies[] = "Dependencies"; - struct sc_service *hsvc; - HKEY hKey; - CHAR str_buffer[ MAX_PATH ]; - LONG r; - DWORD type, val, sz, total, n; - LPSTR p; - - TRACE("%p %p %d %p\n", hService, lpServiceConfig, - cbBufSize, pcbBytesNeeded); - - hsvc = sc_handle_get_handle_data(hService, SC_HTYPE_SERVICE); - if (!hsvc) - { - SetLastError( ERROR_INVALID_HANDLE ); - return FALSE; - } - hKey = hsvc->hkey; + DWORD n; + LPSTR p, buffer; + BOOL ret; + QUERY_SERVICE_CONFIGW *configW;
- /* calculate the size required first */ - total = sizeof (QUERY_SERVICE_CONFIGA); + TRACE("%p %p %d %p\n", hService, config, size, needed);
- sz = sizeof(str_buffer); - r = RegQueryValueExA( hKey, szImagePath, 0, &type, (LPBYTE)str_buffer, &sz ); - if( ( r == ERROR_SUCCESS ) && ( type == REG_SZ || type == REG_EXPAND_SZ ) ) - { - sz = ExpandEnvironmentStringsA(str_buffer,NULL,0); - if( 0 == sz ) return FALSE; - - total += sz; - } - else + if (!(buffer = HeapAlloc( GetProcessHeap(), 0, 2 * size ))) { - /* FIXME: set last error */ - return FALSE; - } - - sz = 0; - r = RegQueryValueExA( hKey, szGroup, 0, &type, NULL, &sz ); - if( ( r == ERROR_SUCCESS ) && ( type == REG_SZ ) ) - total += sz; - - sz = 0; - r = RegQueryValueExA( hKey, szDependencies, 0, &type, NULL, &sz ); - if( ( r == ERROR_SUCCESS ) && ( type == REG_MULTI_SZ ) ) - total += sz; - - sz = 0; - r = RegQueryValueExA( hKey, szStart, 0, &type, NULL, &sz ); - if( ( r == ERROR_SUCCESS ) && ( type == REG_SZ ) ) - total += sz; - - sz = 0; - r = RegQueryValueExA( hKey, szDisplayName, 0, &type, NULL, &sz ); - if( ( r == ERROR_SUCCESS ) && ( type == REG_SZ ) ) - total += sz; - - *pcbBytesNeeded = total; - - /* if there's not enough memory, return an error */ - if( total > cbBufSize ) - { - SetLastError( ERROR_INSUFFICIENT_BUFFER ); + SetLastError( ERROR_NOT_ENOUGH_MEMORY ); return FALSE; } - - ZeroMemory( lpServiceConfig, total ); - - sz = sizeof val; - r = RegQueryValueExA( hKey, szType, 0, &type, (LPBYTE)&val, &sz ); - if( ( r == ERROR_SUCCESS ) || ( type == REG_DWORD ) ) - lpServiceConfig->dwServiceType = val; - - sz = sizeof val; - r = RegQueryValueExA( hKey, szStart, 0, &type, (LPBYTE)&val, &sz ); - if( ( r == ERROR_SUCCESS ) || ( type == REG_DWORD ) ) - lpServiceConfig->dwStartType = val; - - sz = sizeof val; - r = RegQueryValueExA( hKey, szError, 0, &type, (LPBYTE)&val, &sz ); - if( ( r == ERROR_SUCCESS ) || ( type == REG_DWORD ) ) - lpServiceConfig->dwErrorControl = val; - - /* now do the strings */ - p = (LPSTR) &lpServiceConfig[1]; - n = total - sizeof (QUERY_SERVICE_CONFIGA); - - sz = sizeof(str_buffer); - r = RegQueryValueExA( hKey, szImagePath, 0, &type, (LPBYTE)str_buffer, &sz ); - if( ( r == ERROR_SUCCESS ) && ( type == REG_SZ || type == REG_EXPAND_SZ ) ) - { - sz = ExpandEnvironmentStringsA(str_buffer, p, n); - if( 0 == sz || sz > n ) return FALSE; - - lpServiceConfig->lpBinaryPathName = p; - p += sz; - n -= sz; - } - else - { - /* FIXME: set last error */ - return FALSE; - } - - sz = n; - r = RegQueryValueExA( hKey, szGroup, 0, &type, (LPBYTE)p, &sz ); - if( ( r == ERROR_SUCCESS ) || ( type == REG_SZ ) ) - { - lpServiceConfig->lpLoadOrderGroup = p; - p += sz; - n -= sz; - } - - sz = n; - r = RegQueryValueExA( hKey, szDependencies, 0, &type, (LPBYTE)p, &sz ); - if( ( r == ERROR_SUCCESS ) || ( type == REG_SZ ) ) - { - lpServiceConfig->lpDependencies = p; - p += sz; - n -= sz; - } - - if( n < 0 ) - ERR("Buffer overflow!\n"); - - TRACE("Image path = %s\n", lpServiceConfig->lpBinaryPathName ); - TRACE("Group = %s\n", lpServiceConfig->lpLoadOrderGroup ); - - return TRUE; + configW = (QUERY_SERVICE_CONFIGW *)buffer; + ret = QueryServiceConfigW( hService, configW, 2 * size, needed ); + if (!ret) goto done; + + config->dwServiceType = configW->dwServiceType; + config->dwStartType = configW->dwStartType; + config->dwErrorControl = configW->dwErrorControl; + config->lpBinaryPathName = NULL; + config->lpLoadOrderGroup = NULL; + config->dwTagId = configW->dwTagId; + config->lpDependencies = NULL; + config->lpServiceStartName = NULL; + config->lpDisplayName = NULL; + + p = (LPSTR)(config + 1); + n = size - sizeof(*config); + ret = FALSE; + +#define MAP_STR(str) \ + do { \ + if (configW->str) \ + { \ + DWORD sz = WideCharToMultiByte( CP_ACP, 0, configW->str, -1, p, n, NULL, NULL ); \ + if (!sz) goto done; \ + config->str = p; \ + p += sz; \ + n -= sz; \ + } \ + } while (0) + + MAP_STR( lpBinaryPathName ); + MAP_STR( lpLoadOrderGroup ); + MAP_STR( lpDependencies ); + MAP_STR( lpServiceStartName ); + MAP_STR( lpDisplayName ); +#undef MAP_STR + + *needed = p - buffer; + ret = TRUE; + +done: + HeapFree( GetProcessHeap(), 0, buffer ); + return ret; }
/******************************************************************************