Akihiro Sagawa : advapi32: Support the base directory parameter in RegLoadMUIString.
Alexandre Julliard
julliard at winehq.org
Mon May 13 16:24:17 CDT 2019
Module: wine
Branch: master
Commit: 1b7f3698f076458a2bb5aff808ef49f4d2ec8229
URL: https://source.winehq.org/git/wine.git/?a=commit;h=1b7f3698f076458a2bb5aff808ef49f4d2ec8229
Author: Akihiro Sagawa <sagawa.aki at gmail.com>
Date: Thu May 9 22:07:27 2019 +0900
advapi32: Support the base directory parameter in RegLoadMUIString.
Signed-off-by: Akihiro Sagawa <sagawa.aki at gmail.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/advapi32/registry.c | 45 +++++++++++++++++++++++++++++++-----------
dlls/advapi32/tests/registry.c | 4 ++--
dlls/kernel32/time.c | 2 +-
3 files changed, 36 insertions(+), 15 deletions(-)
diff --git a/dlls/advapi32/registry.c b/dlls/advapi32/registry.c
index 43ea3b3..469818c 100644
--- a/dlls/advapi32/registry.c
+++ b/dlls/advapi32/registry.c
@@ -3161,7 +3161,7 @@ static int load_string(HINSTANCE hModule, UINT resId, LPWSTR pwszBuffer, INT cMa
* cbBuffer [I] Size of the destination buffer in bytes.
* pcbData [O] Number of bytes written to pszBuffer (optional, may be NULL).
* dwFlags [I] None supported yet.
- * pszBaseDir [I] Not supported yet.
+ * pszBaseDir [I] Base directory of loading path. If NULL, use the current directory.
*
* RETURNS
* Success: ERROR_SUCCESS,
@@ -3177,7 +3177,7 @@ LSTATUS WINAPI RegLoadMUIStringW(HKEY hKey, LPCWSTR pwszValue, LPWSTR pwszBuffer
DWORD dwValueType, cbData;
LPWSTR pwszTempBuffer = NULL, pwszExpandedBuffer = NULL;
LONG result;
-
+
TRACE("(hKey = %p, pwszValue = %s, pwszBuffer = %p, cbBuffer = %d, pcbData = %p, "
"dwFlags = %d, pwszBaseDir = %s)\n", hKey, debugstr_w(pwszValue), pwszBuffer,
cbBuffer, pcbData, dwFlags, debugstr_w(pwszBaseDir));
@@ -3186,11 +3186,6 @@ LSTATUS WINAPI RegLoadMUIStringW(HKEY hKey, LPCWSTR pwszValue, LPWSTR pwszBuffer
if (!hKey || !pwszBuffer)
return ERROR_INVALID_PARAMETER;
- if (pwszBaseDir && *pwszBaseDir) {
- FIXME("BaseDir parameter not yet supported!\n");
- return ERROR_INVALID_PARAMETER;
- }
-
/* Check for value existence and correctness of its type, allocate a buffer and load it. */
result = RegQueryValueExW(hKey, pwszValue, NULL, &dwValueType, NULL, &cbData);
if (result != ERROR_SUCCESS) goto cleanup;
@@ -3215,7 +3210,7 @@ LSTATUS WINAPI RegLoadMUIStringW(HKEY hKey, LPCWSTR pwszValue, LPWSTR pwszBuffer
result = ERROR_NOT_ENOUGH_MEMORY;
goto cleanup;
}
- ExpandEnvironmentStringsW(pwszTempBuffer, pwszExpandedBuffer, cbData);
+ ExpandEnvironmentStringsW(pwszTempBuffer, pwszExpandedBuffer, cbData / sizeof(WCHAR));
} else {
pwszExpandedBuffer = heap_alloc(cbData);
memcpy(pwszExpandedBuffer, pwszTempBuffer, cbData);
@@ -3227,8 +3222,10 @@ LSTATUS WINAPI RegLoadMUIStringW(HKEY hKey, LPCWSTR pwszValue, LPWSTR pwszBuffer
if (*pwszExpandedBuffer != '@') { /* '@' is the prefix for resource based string entries. */
lstrcpynW(pwszBuffer, pwszExpandedBuffer, cbBuffer / sizeof(WCHAR));
} else {
- WCHAR *pComma = strrchrW(pwszExpandedBuffer, ',');
+ WCHAR *pComma = strrchrW(pwszExpandedBuffer, ','), *pNewBuffer;
+ const WCHAR backslashW[] = {'\\',0};
UINT uiStringId;
+ DWORD baseDirLen;
HMODULE hModule;
/* Format of the expanded value is 'path_to_dll,-resId' */
@@ -3236,17 +3233,41 @@ LSTATUS WINAPI RegLoadMUIStringW(HKEY hKey, LPCWSTR pwszValue, LPWSTR pwszBuffer
result = ERROR_BADKEY;
goto cleanup;
}
-
+
uiStringId = atoiW(pComma+2);
*pComma = '\0';
- hModule = LoadLibraryExW(pwszExpandedBuffer + 1, NULL,
+ /* Build a resource dll path. */
+ baseDirLen = pwszBaseDir ? strlenW(pwszBaseDir) : 0;
+ cbData = (baseDirLen + 1 + strlenW(pwszExpandedBuffer + 1) + 1) * sizeof(WCHAR);
+ pNewBuffer = heap_realloc(pwszTempBuffer, cbData);
+ if (!pNewBuffer) {
+ result = ERROR_NOT_ENOUGH_MEMORY;
+ goto cleanup;
+ }
+ pwszTempBuffer = pNewBuffer;
+ pwszTempBuffer[0] = '\0';
+ if (baseDirLen) {
+ strcpyW(pwszTempBuffer, pwszBaseDir);
+ if (pwszBaseDir[baseDirLen - 1] != '\\')
+ strcatW(pwszTempBuffer, backslashW);
+ }
+ strcatW(pwszTempBuffer, pwszExpandedBuffer + 1);
+
+ /* Verify the file existence. i.e. We don't rely on PATH variable */
+ if (GetFileAttributesW(pwszTempBuffer) == INVALID_FILE_ATTRIBUTES) {
+ result = ERROR_FILE_NOT_FOUND;
+ goto cleanup;
+ }
+
+ /* Load the file */
+ hModule = LoadLibraryExW(pwszTempBuffer, NULL,
LOAD_LIBRARY_AS_DATAFILE | LOAD_LIBRARY_AS_IMAGE_RESOURCE);
if (!hModule || !load_string(hModule, uiStringId, pwszBuffer, cbBuffer/sizeof(WCHAR)))
result = ERROR_BADKEY;
FreeLibrary(hModule);
}
-
+
cleanup:
heap_free(pwszTempBuffer);
heap_free(pwszExpandedBuffer);
diff --git a/dlls/advapi32/tests/registry.c b/dlls/advapi32/tests/registry.c
index f5bcbf3..d6edb02 100644
--- a/dlls/advapi32/tests/registry.c
+++ b/dlls/advapi32/tests/registry.c
@@ -3925,7 +3925,7 @@ static void test_RegLoadMUIString(void)
size = 0xdeadbeef;
memset(bufW, 0xff, sizeof(bufW));
ret = pRegLoadMUIStringW(hkey, tz_valueW, bufW, ARRAY_SIZE(bufW), &size, 0, sysdirW);
- todo_wine ok(ret == ERROR_SUCCESS, "got %d, expected ERROR_SUCCESS\n", ret);
+ ok(ret == ERROR_SUCCESS, "got %d, expected ERROR_SUCCESS\n", ret);
todo_wine ok(size == text_size, "got %u, expected %u\n", size, text_size);
size = min(size, sizeof(bufW));
todo_wine ok(!memcmp(textW, bufW, size), "got %s, expected %s\n",
@@ -3935,7 +3935,7 @@ static void test_RegLoadMUIString(void)
todo_wine ok(ret == ERROR_CALL_NOT_IMPLEMENTED, "got %d, expected ERROR_CALL_NOT_IMPLEMENTED\n", ret);
ret = pRegLoadMUIStringW(hkey, tz_valueW, bufW, ARRAY_SIZE(bufW), &size, 0, NULL);
- todo_wine ok(ret == ERROR_FILE_NOT_FOUND, "got %d, expected ERROR_FILE_NOT_FOUND\n", ret);
+ ok(ret == ERROR_FILE_NOT_FOUND, "got %d, expected ERROR_FILE_NOT_FOUND\n", ret);
ret = pRegLoadMUIStringA(hkey, tz_value, buf, ARRAY_SIZE(buf), &size, 0, NULL);
todo_wine ok(ret == ERROR_CALL_NOT_IMPLEMENTED, "got %d, expected ERROR_CALL_NOT_IMPLEMENTED\n", ret);
diff --git a/dlls/kernel32/time.c b/dlls/kernel32/time.c
index 4a4c494..256cd62 100644
--- a/dlls/kernel32/time.c
+++ b/dlls/kernel32/time.c
@@ -380,7 +380,7 @@ static BOOL reg_load_mui_string(HKEY hkey, LPCWSTR value, LPWSTR buffer, DWORD s
if (hDll) {
pRegLoadMUIStringW = (void *)GetProcAddress(hDll, "RegLoadMUIStringW");
if (pRegLoadMUIStringW &&
- !pRegLoadMUIStringW(hkey, value, buffer, size, NULL, 0, NULL))
+ !pRegLoadMUIStringW(hkey, value, buffer, size, NULL, 0, DIR_System))
ret = TRUE;
FreeLibrary(hDll);
}
More information about the wine-cvs
mailing list