Commit b6e5ee60 authored by Owen Rudge's avatar Owen Rudge Committed by Alexandre Julliard

mapi32: Scan registry for MAPI providers and load them.

parent 7b1f1c71
......@@ -4,7 +4,7 @@ SRCDIR = @srcdir@
VPATH = @srcdir@
MODULE = mapi32.dll
IMPORTLIB = mapi32
IMPORTS = uuid shlwapi shell32 kernel32
IMPORTS = uuid shlwapi shell32 advapi32 kernel32
C_SRCS = \
imalloc.c \
......
/*
* MAPI basics
*
* Copyright 2001 CodeWeavers Inc.
* Copyright 2001, 2009 CodeWeavers Inc.
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
......@@ -29,6 +29,7 @@
#include "mapiform.h"
#include "mapi.h"
#include "wine/debug.h"
#include "util.h"
WINE_DEFAULT_DEBUG_CHANNEL(mapi);
......@@ -45,9 +46,11 @@ BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID fImpLoad)
{
case DLL_PROCESS_ATTACH:
DisableThreadLibraryCalls(hinstDLL);
load_mapi_providers();
break;
case DLL_PROCESS_DETACH:
TRACE("DLL_PROCESS_DETACH: %d objects remaining\n", MAPI_ObjectCount);
unload_mapi_providers();
break;
}
return TRUE;
......
......@@ -2,6 +2,7 @@
* MAPI Utility functions
*
* Copyright 2004 Jon Griffiths
* Copyright 2009 Owen Rudge for CodeWeavers
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
......@@ -37,6 +38,7 @@
#include "mapival.h"
#include "xcmc.h"
#include "msi.h"
#include "util.h"
WINE_DEFAULT_DEBUG_CHANNEL(mapi);
......@@ -903,3 +905,145 @@ HRESULT WINAPI HrQueryAllRows(LPMAPITABLE lpTable, LPSPropTagArray lpPropTags,
*lppRows = NULL;
return MAPI_E_CALL_FAILED;
}
static HMODULE mapi_provider;
static HMODULE mapi_ex_provider;
/**************************************************************************
* load_mapi_provider
*
* Attempts to load a MAPI provider from the specified registry key.
*
* Returns a handle to the loaded module in `mapi_provider' if successful.
*/
static void load_mapi_provider(HKEY hkeyMail, LPCWSTR valueName, HMODULE *mapi_provider)
{
static const WCHAR mapi32_dll[] = {'m','a','p','i','3','2','.','d','l','l',0 };
DWORD dwType, dwLen = 0;
LPWSTR dllPath;
/* Check if we have a value set for DLLPath */
if ((RegQueryValueExW(hkeyMail, valueName, NULL, &dwType, NULL, &dwLen) == ERROR_SUCCESS) &&
((dwType == REG_SZ) || (dwType == REG_EXPAND_SZ)) && (dwLen > 0))
{
dllPath = HeapAlloc(GetProcessHeap(), 0, dwLen);
if (dllPath)
{
RegQueryValueExW(hkeyMail, valueName, NULL, NULL, (LPBYTE)dllPath, &dwLen);
/* Check that this value doesn't refer to mapi32.dll (eg, as Outlook does) */
if (lstrcmpiW(dllPath, mapi32_dll) != 0)
{
if (dwType == REG_EXPAND_SZ)
{
DWORD dwExpandLen;
LPWSTR dllPathExpanded;
/* Expand the path if necessary */
dwExpandLen = ExpandEnvironmentStringsW(dllPath, NULL, 0);
dllPathExpanded = HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR) * dwExpandLen + 1);
if (dllPathExpanded)
{
ExpandEnvironmentStringsW(dllPath, dllPathExpanded, dwExpandLen + 1);
HeapFree(GetProcessHeap(), 0, dllPath);
dllPath = dllPathExpanded;
}
}
/* Load the DLL */
TRACE("loading %s\n", debugstr_w(dllPath));
*mapi_provider = LoadLibraryW(dllPath);
}
HeapFree(GetProcessHeap(), 0, dllPath);
}
}
}
/**************************************************************************
* load_mapi_providers
*
* Scans the registry for MAPI providers and attempts to load a Simple and
* Extended MAPI library.
*
* Returns TRUE if at least one library loaded, FALSE otherwise.
*/
void load_mapi_providers(void)
{
static const WCHAR regkey_mail[] = {
'S','o','f','t','w','a','r','e','\\','C','l','i','e','n','t','s','\\',
'M','a','i','l',0 };
static const WCHAR regkey_dllpath[] = {'D','L','L','P','a','t','h',0 };
static const WCHAR regkey_dllpath_ex[] = {'D','L','L','P','a','t','h','E','x',0 };
static const WCHAR regkey_backslash[] = { '\\', 0 };
HKEY hkeyMail;
DWORD dwType, dwLen = 0;
LPWSTR appName = NULL, appKey = NULL;
TRACE("()\n");
/* Open the Mail key */
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, regkey_mail, 0, KEY_READ, &hkeyMail) != ERROR_SUCCESS)
return;
/* Check if we have a default value set, and the length of it */
if ((RegQueryValueExW(hkeyMail, NULL, NULL, &dwType, NULL, &dwLen) != ERROR_SUCCESS) ||
!((dwType == REG_SZ) || (dwType == REG_EXPAND_SZ)) || (dwLen == 0))
goto cleanUp;
appName = HeapAlloc(GetProcessHeap(), 0, dwLen);
if (!appName)
goto cleanUp;
/* Get the value, and get the path to the app key */
RegQueryValueExW(hkeyMail, NULL, NULL, NULL, (LPBYTE)appName, &dwLen);
TRACE("appName: %s\n", debugstr_w(appName));
appKey = HeapAlloc(GetProcessHeap(), 0, sizeof(WCHAR) * (lstrlenW(regkey_mail) +
lstrlenW(regkey_backslash) + lstrlenW(appName)));
if (!appKey)
goto cleanUp;
lstrcpyW(appKey, regkey_mail);
lstrcatW(appKey, regkey_backslash);
lstrcatW(appKey, appName);
RegCloseKey(hkeyMail);
TRACE("appKey: %s\n", debugstr_w(appKey));
/* Open the app's key */
if (RegOpenKeyExW(HKEY_LOCAL_MACHINE, appKey, 0, KEY_READ, &hkeyMail) != ERROR_SUCCESS)
return;
/* Try to load the providers */
load_mapi_provider(hkeyMail, regkey_dllpath, &mapi_provider);
load_mapi_provider(hkeyMail, regkey_dllpath_ex, &mapi_ex_provider);
cleanUp:
RegCloseKey(hkeyMail);
HeapFree(GetProcessHeap(), 0, appKey);
HeapFree(GetProcessHeap(), 0, appName);
}
/**************************************************************************
* unload_mapi_providers
*
* Unloads any loaded MAPI libraries.
*/
void unload_mapi_providers(void)
{
TRACE("()\n");
FreeLibrary(mapi_provider);
FreeLibrary(mapi_ex_provider);
}
/*
* MAPI utility header file
*
* Copyright 2009 Owen Rudge for CodeWeavers
*
* This library is free software; you can redistribute it and/or
* modify it under the terms of the GNU Lesser General Public
* License as published by the Free Software Foundation; either
* version 2.1 of the License, or (at your option) any later version.
*
* This library is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
* Lesser General Public License for more details.
*
* You should have received a copy of the GNU Lesser General Public
* License along with this library; if not, write to the Free Software
* Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA
*/
#ifndef _MAPI_UTIL_H
#define _MAPI_UTIL_H
extern void load_mapi_providers(void);
extern void unload_mapi_providers(void);
#endif
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