Rémi Bernon : mscoree: Fallback to assembly name if codebase path is invalid.

Alexandre Julliard julliard at winehq.org
Tue Mar 23 15:07:44 CDT 2021


Module: wine
Branch: oldstable
Commit: 4264a498a02f3df1fa2e3123c9649f84402b8f72
URL:    https://source.winehq.org/git/wine.git/?a=commit;h=4264a498a02f3df1fa2e3123c9649f84402b8f72

Author: Rémi Bernon <rbernon at codeweavers.com>
Date:   Fri Oct 23 08:51:46 2020 +0200

mscoree: Fallback to assembly name if codebase path is invalid.

Also use the InprocServer32 key values if there's no subkeys, as shown
by the test results.

L.A.Noire game crashes on startup after failing to load its ErrorHandler
assembly, that has an invalid CodeBase path in the registry.

Signed-off-by: Rémi Bernon <rbernon at codeweavers.com>
Signed-off-by: Esme Povirk <esme at codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
(cherry picked from commit 7b0a939a1fb9f0acc7b450cd849fb4e1d93eb499)
Signed-off-by: Michael Stefaniuc <mstefani at winehq.org>

---

 dlls/mscoree/corruntimehost.c | 44 +++++++++++++++++++++++++++++--------------
 dlls/mscoree/tests/comtest.c  |  3 ++-
 2 files changed, 32 insertions(+), 15 deletions(-)

diff --git a/dlls/mscoree/corruntimehost.c b/dlls/mscoree/corruntimehost.c
index a900ed6a3e2..886267546c5 100644
--- a/dlls/mscoree/corruntimehost.c
+++ b/dlls/mscoree/corruntimehost.c
@@ -1759,6 +1759,7 @@ HRESULT create_monodata(REFIID riid, LPVOID *ppObj )
     HKEY key, subkey;
     LONG res;
     int offset = 0;
+    HANDLE file = INVALID_HANDLE_VALUE;
     DWORD numKeys, keyLength;
     WCHAR codebase[MAX_PATH + 8];
     WCHAR classname[350], subkeyName[256];
@@ -1794,7 +1795,12 @@ HRESULT create_monodata(REFIID riid, LPVOID *ppObj )
                 offset = lstrlenW(wszFileSlash);
 
             lstrcpyW(filename, codebase + offset);
+
+            file = CreateFileW(path, GENERIC_READ, 0, NULL, OPEN_EXISTING, 0, 0);
         }
+
+        if (file != INVALID_HANDLE_VALUE)
+            CloseHandle(file);
         else
         {
             WCHAR assemblyname[MAX_PATH + 8];
@@ -1803,27 +1809,37 @@ HRESULT create_monodata(REFIID riid, LPVOID *ppObj )
             WARN("CodeBase value cannot be found, trying Assembly.\n");
             /* get the last subkey of InprocServer32 */
             res = RegQueryInfoKeyW(key, 0, 0, 0, &numKeys, 0, 0, 0, 0, 0, 0, 0);
-            if (res != ERROR_SUCCESS || numKeys == 0)
-                goto cleanup;
-            numKeys--;
-            keyLength = ARRAY_SIZE(subkeyName);
-            res = RegEnumKeyExW(key, numKeys, subkeyName, &keyLength, 0, 0, 0, 0);
-            if (res != ERROR_SUCCESS)
-                goto cleanup;
-            res = RegOpenKeyExW(key, subkeyName, 0, KEY_READ, &subkey);
-            if (res != ERROR_SUCCESS)
-                goto cleanup;
-            dwBufLen = MAX_PATH + 8;
-            res = RegGetValueW(subkey, NULL, wszAssembly, RRF_RT_REG_SZ, NULL, assemblyname, &dwBufLen);
-            RegCloseKey(subkey);
             if (res != ERROR_SUCCESS)
                 goto cleanup;
+            if (numKeys > 0)
+            {
+                numKeys--;
+                keyLength = ARRAY_SIZE(subkeyName);
+                res = RegEnumKeyExW(key, numKeys, subkeyName, &keyLength, 0, 0, 0, 0);
+                if (res != ERROR_SUCCESS)
+                    goto cleanup;
+                res = RegOpenKeyExW(key, subkeyName, 0, KEY_READ, &subkey);
+                if (res != ERROR_SUCCESS)
+                    goto cleanup;
+                dwBufLen = MAX_PATH + 8;
+                res = RegGetValueW(subkey, NULL, wszAssembly, RRF_RT_REG_SZ, NULL, assemblyname, &dwBufLen);
+                RegCloseKey(subkey);
+                if (res != ERROR_SUCCESS)
+                    goto cleanup;
+            }
+            else
+            {
+                dwBufLen = MAX_PATH + 8;
+                res = RegGetValueW(key, NULL, wszAssembly, RRF_RT_REG_SZ, NULL, assemblyname, &dwBufLen);
+                if (res != ERROR_SUCCESS)
+                    goto cleanup;
+            }
 
             hr = get_file_from_strongname(assemblyname, filename, MAX_PATH);
             if (FAILED(hr))
             {
                 /*
-                 * The registry doesn't have a CodeBase entry and it's not in the GAC.
+                 * The registry doesn't have a CodeBase entry or the file isn't there, and it's not in the GAC.
                  *
                  * Use the Assembly Key to retrieve the filename.
                  *    Assembly : REG_SZ : AssemblyName, Version=X.X.X.X, Culture=neutral, PublicKeyToken=null
diff --git a/dlls/mscoree/tests/comtest.c b/dlls/mscoree/tests/comtest.c
index 63df3219a79..87d7626a3dd 100644
--- a/dlls/mscoree/tests/comtest.c
+++ b/dlls/mscoree/tests/comtest.c
@@ -177,7 +177,8 @@ static void run_registry_test(run_type run)
     ok(ret == ERROR_SUCCESS, "RegSetKeyValueA returned %x\n", ret);
 
     hr = CoCreateInstance(&CLSID_Test, NULL, CLSCTX_INPROC_SERVER, &IID_ITest, (void**)&test);
-    todo_wine ok(hr == result_expected, "Expected %x, got %x\n", result_expected, hr);
+    todo_wine_if(result_expected != S_OK)
+    ok(hr == result_expected, "Expected %x, got %x\n", result_expected, hr);
 
     if (hr == S_OK)
     {




More information about the wine-cvs mailing list