From 69b89379f9577d9c9c78096fdaaba82634b58b39 Mon Sep 17 00:00:00 2001 From: Lei Zhang Date: Tue, 14 Oct 2008 15:06:45 -0700 Subject: [PATCH] shlwapi: Properly handle pszExtra in IQueryAssociations_GetString. --- dlls/shlwapi/assoc.c | 26 +++++++++++++++- dlls/shlwapi/tests/assoc.c | 72 ++++++++++++++++++++++++++++++++++++++++++++ 2 files changed, 97 insertions(+), 1 deletions(-) diff --git a/dlls/shlwapi/assoc.c b/dlls/shlwapi/assoc.c index 7f71708..4a67d82 100644 --- a/dlls/shlwapi/assoc.c +++ b/dlls/shlwapi/assoc.c @@ -627,7 +627,31 @@ static HRESULT ASSOC_GetExecutable(IQueryAssociationsImpl *This, if (!pszExtra) { hr = ASSOC_GetValue(hkeyShell, &pszExtraFromReg); - if (FAILED(hr)) + /* if no default action */ + if (hr == E_FAIL || hr == HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND)) + { + DWORD rlen; + ret = RegQueryInfoKeyW(hkeyShell, 0, 0, 0, 0, &rlen, 0, 0, 0, 0, 0, 0); + if (ret != ERROR_SUCCESS) + { + RegCloseKey(hkeyShell); + return HRESULT_FROM_WIN32(ret); + } + rlen++; + pszExtraFromReg = HeapAlloc(GetProcessHeap(), 0, rlen * sizeof(WCHAR)); + if (!pszExtraFromReg) + { + RegCloseKey(hkeyShell); + return E_OUTOFMEMORY; + } + ret = RegEnumKeyExW(hkeyShell, 0, pszExtraFromReg, &rlen, 0, NULL, NULL, NULL); + if (ret != ERROR_SUCCESS) + { + RegCloseKey(hkeyShell); + return HRESULT_FROM_WIN32(ret); + } + } + else if (FAILED(hr)) { RegCloseKey(hkeyShell); return hr; diff --git a/dlls/shlwapi/tests/assoc.c b/dlls/shlwapi/tests/assoc.c index e5d40d1..2e383bb 100644 --- a/dlls/shlwapi/tests/assoc.c +++ b/dlls/shlwapi/tests/assoc.c @@ -32,6 +32,19 @@ static const WCHAR dotBad[] = { '.','b','a','d',0 }; static const WCHAR open[] = { 'o','p','e','n',0 }; static const WCHAR invalid[] = { 'i','n','v','a','l','i','d',0 }; +/* copied from libs/wine/string.c */ +WCHAR *strstrW(const WCHAR *str, const WCHAR *sub) +{ + while (*str) + { + const WCHAR *p1 = str, *p2 = sub; + while (*p1 && *p2 && *p1 == *p2) { p1++; p2++; } + if (!*p2) return (WCHAR *)str; + str++; + } + return NULL; +} + static void test_getstring_bad(void) { HRESULT hr; @@ -127,8 +140,67 @@ static void test_getstring_basic(void) HeapFree(GetProcessHeap(), 0, friendlyName); } +static void test_getstring_no_extra(void) +{ + LONG ret; + HKEY hkey; + HRESULT hr; + static const WCHAR dotWinetest[] = { + '.','w','i','n','e','t','e','s','t',0 + }; + static const WCHAR winetestfile[] = { + 'w','i','n','e','t','e','s','t', 'f','i','l','e',0 + }; + static const WCHAR winetestfileAction[] = { + 'w','i','n','e','t','e','s','t','f','i','l','e', + '\\','s','h','e','l','l', + '\\','f','o','o', + '\\','c','o','m','m','a','n','d',0 + }; + static const WCHAR action[] = { + 'n','o','t','e','p','a','d','.','e','x','e',0 + }; + WCHAR buf[MAX_PATH]; + DWORD len = MAX_PATH; + + ret = RegCreateKeyW(HKEY_CLASSES_ROOT, dotWinetest, &hkey); + if (ret != ERROR_SUCCESS) + skip("failed to create dotWinetest key\n"); + ret = RegSetValueW(hkey, NULL, REG_SZ, winetestfile, + lstrlenW(winetestfile)); + RegCloseKey(hkey); + if (ret != ERROR_SUCCESS) + { + RegDeleteTreeW(HKEY_CLASSES_ROOT, dotWinetest); + skip("failed to set dotWinetest key\n"); + } + + ret = RegCreateKeyW(HKEY_CLASSES_ROOT, winetestfileAction, &hkey); + if (ret != ERROR_SUCCESS) + { + RegDeleteTreeW(HKEY_CLASSES_ROOT, dotWinetest); + skip("failed to create winetestfileAction key\n"); + } + ret = RegSetValueW(hkey, NULL, REG_SZ, action, lstrlenW(action)); + RegCloseKey(hkey); + if (ret != ERROR_SUCCESS) + { + RegDeleteTreeW(HKEY_CLASSES_ROOT, dotWinetest); + RegDeleteTreeW(HKEY_CLASSES_ROOT, winetestfile); + skip("failed to set winetestfileAction key\n"); + } + + hr = AssocQueryStringW(0, ASSOCSTR_EXECUTABLE, dotWinetest, NULL, + buf, &len); + expect_hr(S_OK, hr); + ok(strstrW(buf, action) != NULL, "exe path does not contain notepad\n"); + RegDeleteTreeW(HKEY_CLASSES_ROOT, dotWinetest); + RegDeleteTreeW(HKEY_CLASSES_ROOT, winetestfile); +} + START_TEST(assoc) { test_getstring_bad(); test_getstring_basic(); + test_getstring_no_extra(); } -- 1.5.4.5