Commit 3c9720f4 authored by Dmitry Timoshkov's avatar Dmitry Timoshkov Committed by Alexandre Julliard

combase: Execute local server for correct architecture in a WoW64 setup.

Based on implementation of create_surrogate_server(). This patch makes 64-bit application work with its own shipped 32-bit COM server. Signed-off-by: 's avatarDmitry Timoshkov <dmitry@baikal.ru> Signed-off-by: 's avatarHuw Davies <huw@codeweavers.com> Signed-off-by: 's avatarAlexandre Julliard <julliard@winehq.org>
parent 9ba69dce
......@@ -477,6 +477,9 @@ static HRESULT create_server(REFCLSID rclsid, HANDLE *process)
{
static const WCHAR embeddingW[] = L" -Embedding";
HKEY key;
int arch = (sizeof(void *) > sizeof(int)) ? 64 : 32;
REGSAM opposite = (arch == 64) ? KEY_WOW64_32KEY : KEY_WOW64_64KEY;
BOOL is_wow64 = FALSE, is_opposite = FALSE;
HRESULT hr;
WCHAR command[MAX_PATH + ARRAY_SIZE(embeddingW)];
DWORD size = (MAX_PATH+1) * sizeof(WCHAR);
......@@ -484,7 +487,14 @@ static HRESULT create_server(REFCLSID rclsid, HANDLE *process)
PROCESS_INFORMATION pinfo;
LONG ret;
TRACE("Attempting to start server for %s\n", debugstr_guid(rclsid));
hr = open_key_for_clsid(rclsid, L"LocalServer32", KEY_READ, &key);
if (FAILED(hr) && (arch == 64 || (IsWow64Process(GetCurrentProcess(), &is_wow64) && is_wow64)))
{
hr = open_key_for_clsid(rclsid, L"LocalServer32", opposite | KEY_READ, &key);
is_opposite = TRUE;
}
if (FAILED(hr))
{
ERR("class %s not registered\n", debugstr_guid(rclsid));
......@@ -510,9 +520,21 @@ static HRESULT create_server(REFCLSID rclsid, HANDLE *process)
/* FIXME: Win2003 supports a ServerExecutable value that is passed into
* CreateProcess */
if (is_opposite)
{
void *cookie;
Wow64DisableWow64FsRedirection(&cookie);
if (!CreateProcessW(NULL, command, NULL, NULL, FALSE, DETACHED_PROCESS, NULL, NULL, &sinfo, &pinfo))
{
WARN("failed to run local server %s\n", debugstr_w(command));
hr = HRESULT_FROM_WIN32(GetLastError());
}
Wow64RevertWow64FsRedirection(cookie);
if (FAILED(hr)) return hr;
}
else if (!CreateProcessW(NULL, command, NULL, NULL, FALSE, DETACHED_PROCESS, NULL, NULL, &sinfo, &pinfo))
{
WARN("failed to run local server %s\n", debugstr_w(command));
return HRESULT_FROM_WIN32(GetLastError());
}
*process = pinfo.hProcess;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment