wshom: Basic support for REG_SZ values in RegRead()

Nikolay Sivov nsivov at codeweavers.com
Mon Dec 3 05:29:27 CST 2012


http://bugs.winehq.org/show_bug.cgi?id=32315
-------------- next part --------------
>From 6f3e45d3f7d6b972a8f2391ec3ab0f2aa8563de5 Mon Sep 17 00:00:00 2001
From: Nikolay Sivov <nsivov at codeweavers.com>
Date: Sun, 2 Dec 2012 13:58:10 +0400
Subject: [PATCH 1/1] Basic support for REG_SZ values in RegRead()

---
 dlls/wshom.ocx/shell.c           |   63 +++++++++++++++++++++++++--
 dlls/wshom.ocx/tests/Makefile.in |    2 +-
 dlls/wshom.ocx/tests/wshom.c     |   89 ++++++++++++++++++++++++++++++++------
 3 files changed, 137 insertions(+), 17 deletions(-)

diff --git a/dlls/wshom.ocx/shell.c b/dlls/wshom.ocx/shell.c
index 1973e2d..4f64449 100644
--- a/dlls/wshom.ocx/shell.c
+++ b/dlls/wshom.ocx/shell.c
@@ -690,10 +690,67 @@ static HRESULT WINAPI WshShell3_ExpandEnvironmentStrings(IWshShell3 *iface, BSTR
     return E_NOTIMPL;
 }
 
-static HRESULT WINAPI WshShell3_RegRead(IWshShell3 *iface, BSTR Name, VARIANT* out_Value)
+static HRESULT WINAPI WshShell3_RegRead(IWshShell3 *iface, BSTR name, VARIANT* value)
 {
-    FIXME("(%s %p): stub\n", debugstr_w(Name), out_Value);
-    return E_NOTIMPL;
+    static const WCHAR hkcuW[] = {'H','K','E','Y','_','C','U','R','R','E','N','T','_','U','S','E','R'};
+    static const WCHAR hkcrW[] = {'H','K','E','Y','_','C','L','A','S','S','E','S','_','R','O','O','T'};
+    static const WCHAR hklmW[] = {'H','K','E','Y','_','L','O','C','A','L','_','M','A','C','H','I','N','E'};
+    DWORD type, len, datalen, val;
+    BSTR keyname;
+    HKEY root;
+    LONG ret;
+
+    TRACE("(%s %p)\n", debugstr_w(name), value);
+
+    /* get root from a name */
+    if (!strncmpW(name, hkcuW, sizeof(hkcuW)/sizeof(WCHAR)))
+    {
+        root = HKEY_CURRENT_USER;
+        len = sizeof(hkcuW)/sizeof(WCHAR);
+    }
+    else if (!strncmpW(name, hkcrW, sizeof(hkcrW)/sizeof(WCHAR)))
+    {
+        root = HKEY_CLASSES_ROOT;
+        len = sizeof(hkcrW)/sizeof(WCHAR);
+    }
+    else if (!strncmpW(name, hklmW, sizeof(hklmW)/sizeof(WCHAR)))
+    {
+        root = HKEY_LOCAL_MACHINE;
+        len = sizeof(hklmW)/sizeof(WCHAR);
+    }
+    else
+    {
+        FIXME("root unrecognized %s\n", debugstr_w(name));
+        return E_FAIL;
+    }
+
+    /* skip '\' after root name */
+    if (name[len] == '\\') len++;
+
+    val = strlenW(name);
+    while (name[--val] != '\\' && val)
+        ;
+    keyname = SysAllocStringLen(&name[len], val-len);
+    /* skip leading '\' */
+    val++;
+
+    type = REG_NONE;
+    datalen = 0;
+    ret = RegGetValueW(root, keyname, &name[val], RRF_RT_ANY, &type, NULL, &datalen);
+    if (ret == ERROR_SUCCESS)
+    {
+        if (type == REG_SZ)
+        {
+            V_VT(value) = VT_BSTR;
+            V_BSTR(value) = SysAllocStringLen(NULL, datalen-1);
+            ret = RegGetValueW(root, keyname, &name[val], RRF_RT_ANY, &type, V_BSTR(value), &datalen);
+        }
+        else
+            FIXME("type %d not handled\n", type);
+    }
+
+    SysFreeString(keyname);
+    return HRESULT_FROM_WIN32(ret);
 }
 
 static HRESULT WINAPI WshShell3_RegWrite(IWshShell3 *iface, BSTR Name, VARIANT *Value, VARIANT *Type)
diff --git a/dlls/wshom.ocx/tests/Makefile.in b/dlls/wshom.ocx/tests/Makefile.in
index 1580050..122a1e1 100644
--- a/dlls/wshom.ocx/tests/Makefile.in
+++ b/dlls/wshom.ocx/tests/Makefile.in
@@ -1,5 +1,5 @@
 TESTDLL   = wshom.ocx
-IMPORTS   = oleaut32 ole32
+IMPORTS   = oleaut32 ole32 advapi32
 
 C_SRCS = \
 	wshom.c
diff --git a/dlls/wshom.ocx/tests/wshom.c b/dlls/wshom.ocx/tests/wshom.c
index b2f60a8..f62c43b 100644
--- a/dlls/wshom.ocx/tests/wshom.c
+++ b/dlls/wshom.ocx/tests/wshom.c
@@ -28,6 +28,8 @@
 
 DEFINE_GUID(GUID_NULL,0,0,0,0,0,0,0,0,0,0,0);
 
+static IWshShell3 *sh3;
+
 #define EXPECT_HR(hr,hr_exp) \
     ok(hr == hr_exp, "got 0x%08x, expected 0x%08x\n", hr, hr_exp)
 
@@ -35,7 +37,6 @@ static void test_wshshell(void)
 {
     static const WCHAR desktopW[] = {'D','e','s','k','t','o','p',0};
     static const WCHAR lnk1W[] = {'f','i','l','e','.','l','n','k',0};
-    IWshShell3 *sh3;
     IDispatchEx *dispex;
     IWshCollection *coll;
     IDispatch *disp, *shortcut;
@@ -50,23 +51,16 @@ static void test_wshshell(void)
     BSTR str;
     UINT err;
 
-    hr = CoCreateInstance(&CLSID_WshShell, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
-            &IID_IDispatch, (void**)&disp);
-    if(FAILED(hr)) {
-        win_skip("Could not create WshShell object: %08x\n", hr);
-        return;
-    }
+    hr = IWshShell3_QueryInterface(sh3, &IID_IDispatch, (void**)&disp);
+    ok(hr == S_OK, "got 0x%08x\n", hr);
 
     hr = IDispatch_QueryInterface(disp, &IID_IWshShell3, (void**)&shell);
     EXPECT_HR(hr, S_OK);
-    IDispatch_Release(disp);
+    IUnknown_Release(shell);
 
     hr = IDispatch_QueryInterface(disp, &IID_IDispatchEx, (void**)&dispex);
     EXPECT_HR(hr, E_NOINTERFACE);
 
-    hr = IUnknown_QueryInterface(shell, &IID_IWshShell3, (void**)&sh3);
-    EXPECT_HR(hr, S_OK);
-
     hr = IWshShell3_get_SpecialFolders(sh3, &coll);
     EXPECT_HR(hr, S_OK);
 
@@ -115,15 +109,84 @@ static void test_wshshell(void)
 
     IWshCollection_Release(coll);
     IDispatch_Release(disp);
-    IWshShell3_Release(sh3);
-    IUnknown_Release(shell);
+}
+
+/* delete key and all its subkeys */
+static DWORD delete_key(HKEY hkey)
+{
+    char name[MAX_PATH];
+    DWORD ret;
+
+    while (!(ret = RegEnumKeyA(hkey, 0, name, sizeof(name))))
+    {
+        HKEY tmp;
+        if (!(ret = RegOpenKeyExA(hkey, name, 0, KEY_ENUMERATE_SUB_KEYS, &tmp)))
+        {
+            ret = delete_key(tmp);
+            RegCloseKey(tmp);
+        }
+        if (ret) break;
+    }
+    if (ret != ERROR_NO_MORE_ITEMS) return ret;
+    RegDeleteKeyA(hkey, "");
+    return 0;
+}
+
+static void test_registry(void)
+{
+    static const WCHAR regszW[] = {'H','K','E','Y','_','C','U','R','R','E','N','T','_','U','S','E','R','\\',
+        'S','o','f','t','w','a','r','e','\\','W','i','n','e','\\','T','e','s','t','\\','r','e','g','s','z',0};
+    static const WCHAR regsz1W[] = {'H','K','E','Y','_','C','U','R','R','E','N','T','_','U','S','E','R','\\',
+        'S','o','f','t','w','a','r','e','\\','W','i','n','e','\\','T','e','s','t','\\','r','e','g','s','z','1',0};
+    static const WCHAR foobarW[] = {'f','o','o','b','a','r',0};
+    VARIANT value;
+    HRESULT hr;
+    HKEY root;
+    LONG ret;
+    BSTR name;
+
+    ret = RegCreateKeyA(HKEY_CURRENT_USER, "Software\\Wine\\Test", &root);
+    ok(ret == 0, "got %d\n", ret);
+
+    ret = RegSetValueExA(root, "regsz", 0, REG_SZ, (const BYTE *)"foobar", 7 );
+    ok(ret == 0, "got %d\n", ret);
+
+    name = SysAllocString(regszW);
+    VariantInit(&value);
+    hr = IWshShell3_RegRead(sh3, name, &value);
+    ok(hr == S_OK, "got 0x%08x\n", hr);
+    ok(V_VT(&value) == VT_BSTR, "got %d\n", V_VT(&value));
+    ok(!lstrcmpW(V_BSTR(&value), foobarW), "got %s\n", wine_dbgstr_w(V_BSTR(&value)));
+    VariantClear(&value);
+    SysFreeString(name);
+
+    name = SysAllocString(regsz1W);
+    V_VT(&value) = VT_NULL;
+    hr = IWshShell3_RegRead(sh3, name, &value);
+    ok(hr == HRESULT_FROM_WIN32(ERROR_FILE_NOT_FOUND), "got 0x%08x\n", hr);
+    ok(V_VT(&value) == VT_NULL, "got %d\n", V_VT(&value));
+    VariantClear(&value);
+    SysFreeString(name);
+
+    delete_key(root);
 }
 
 START_TEST(wshom)
 {
+    HRESULT hr;
+
     CoInitialize(NULL);
 
+    hr = CoCreateInstance(&CLSID_WshShell, NULL, CLSCTX_INPROC_SERVER|CLSCTX_INPROC_HANDLER,
+            &IID_IWshShell3, (void**)&sh3);
+    if(FAILED(hr)) {
+        win_skip("Could not create WshShell object: %08x\n", hr);
+        return;
+    }
+
     test_wshshell();
+    test_registry();
 
+    IWshShell3_Release(sh3);
     CoUninitialize();
 }
-- 
1.7.10.4



More information about the wine-patches mailing list