Source code of Windows XP (NT5)
You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
|
|
//+----------------------------------------------------------------------------
//
// File: ShellDll.cpp
//
// Module: Common Code
//
// Synopsis: Implements the class CShellDll, a shell32.dll wrapper.
//
// Copyright (c) 1999 Microsoft Corporation
//
// Author: fengsun Created 01/12/98
//
//+----------------------------------------------------------------------------
//+----------------------------------------------------------------------------
//
// Function: CShellDll::CShellDll
//
// Synopsis: Constructor
//
// Arguments: None
//
// Returns: Nothing
//
// History: Created Header 2/17/98
//
//+----------------------------------------------------------------------------
CShellDll::CShellDll(BOOL fKeepDllLoaded) { m_hInstShell = NULL; m_fnShellExecuteEx = NULL; m_fnShell_NotifyIcon = NULL; m_pfnSHGetSpecialFolderLocation = NULL; m_pfnSHGetPathFromIDList = NULL; m_pfnSHGetMalloc = NULL; m_KeepDllLoaded = fKeepDllLoaded; }
//+----------------------------------------------------------------------------
//
// Function: CShellDll::~CShellDl
//
// Synopsis: Destructor
//
// Arguments: None
//
// Returns: Nothing
//
// History: Created Header 2/17/98
//
//+----------------------------------------------------------------------------
CShellDll::~CShellDll() { Unload(); }
//+----------------------------------------------------------------------------
//
// Function: CShellDll::Load
//
// Synopsis: Load shell32.dll
// It works even if the dll is already loaded, but we do not keep a referrence
// count here, any unload call will unload the dll
//
// Arguments: None
//
// Returns: BOOL - Whether the dll is successfully loaded
//
// History: fengsun Created Header 1/12/98
//
//+----------------------------------------------------------------------------
BOOL CShellDll::Load() { //
// Simply return, if already loaded
//
LPSTR pszShellExecuteEx; LPSTR pszShellNotifyIcon; LPSTR pszSHGetPathFromIDList; LPSTR pszSHGetSpecialFolderLocation; LPSTR pszSHGetMalloc;
if (m_hInstShell == NULL) { if (OS_NT) { m_hInstShell = LoadLibraryExA("Shell32.dll", NULL, 0); pszShellExecuteEx = "ShellExecuteExW"; pszShellNotifyIcon = "Shell_NotifyIconW"; pszSHGetPathFromIDList = "SHGetPathFromIDListW"; pszSHGetSpecialFolderLocation = "SHGetSpecialFolderLocation"; // no A or W version
pszSHGetMalloc = "SHGetMalloc"; // no A or W version
} else { m_hInstShell = LoadLibraryExA("cmutoa.dll", NULL, 0); pszShellExecuteEx = "ShellExecuteExUA"; pszShellNotifyIcon = "Shell_NotifyIconUA"; pszSHGetPathFromIDList = "SHGetPathFromIDListUA"; pszSHGetSpecialFolderLocation = "SHGetSpecialFolderLocationUA"; // no actual A or W version
pszSHGetMalloc = "SHGetMallocUA"; // but this class only
// allows one dll
}
if (m_hInstShell == NULL) { return FALSE; }
m_pfnSHGetMalloc = (SHGetMallocSpec)GetProcAddress(m_hInstShell, pszSHGetMalloc); m_pfnSHGetSpecialFolderLocation = (SHGetSpecialFolderLocationSpec)GetProcAddress(m_hInstShell, pszSHGetSpecialFolderLocation); m_pfnSHGetPathFromIDList = (SHGetPathFromIDListSpec)GetProcAddress(m_hInstShell, pszSHGetPathFromIDList); m_fnShellExecuteEx = (SHELLEXECUTEEXPROC)GetProcAddress(m_hInstShell, pszShellExecuteEx); m_fnShell_NotifyIcon = (SHELL_NOTIFYICONPROC)GetProcAddress(m_hInstShell, pszShellNotifyIcon);
if (NULL == m_fnShellExecuteEx || NULL == m_fnShell_NotifyIcon || NULL == m_pfnSHGetSpecialFolderLocation || NULL == m_pfnSHGetPathFromIDList || NULL == m_pfnSHGetMalloc) { FreeLibrary(m_hInstShell); m_hInstShell = NULL; return FALSE; } }
return TRUE; }
//+----------------------------------------------------------------------------
//
// Function: CShellDll::Unload
//
// Synopsis: Unload the shell32.dll
//
// Arguments: None
//
// Returns: Nothing
//
// History: fengsun Created Header 1/12/98
//
//+----------------------------------------------------------------------------
void CShellDll::Unload() { if (m_hInstShell == NULL) { return; } //
// Don't release library because of shell bug #289463 + #371836
// ShellExecute fires a thread which wakes up after the release
// of the library and crashes us. Ugly but real, we have no choice
// but to stay linked to the Shell DLL.
//
if (!m_KeepDllLoaded) { FreeLibrary(m_hInstShell); m_hInstShell = NULL; } }
//+----------------------------------------------------------------------------
//
// Function: CShellDll::ShellGetSpecialFolderLocation
//
// Synopsis: Wrapper function for SHGetSpecialFolderLocation. Please note the
// returned pidl must be freed with the Shell's Malloc pointer (use SHGetMalloc).
//
// Arguments: Please see the api definition for SHGetSpecialFolderLocation
//
// Returns: HRESULT - standard COM error codes
//
// History: quintinb Created 5/21/99
//
//+----------------------------------------------------------------------------
HRESULT CShellDll::ShellGetSpecialFolderLocation(HWND hwnd, int csidl, LPITEMIDLIST *ppidl) { if (!Load()) { return E_FAIL; }
return m_pfnSHGetSpecialFolderLocation(hwnd, csidl, ppidl); }
//+----------------------------------------------------------------------------
//
// Function: CShellDll::ShellGetPathFromIDList
//
// Synopsis: Wrapper function for SHGetPathFromIDList.
//
// Arguments: Please see the api definition for SHGetPathFromIDList
//
// Returns: BOOL - TRUE on success
//
// History: quintinb Created 5/21/99
//
//+----------------------------------------------------------------------------
BOOL CShellDll::ShellGetPathFromIDList(LPCITEMIDLIST pidl, LPTSTR pszPath) { if (!Load()) { return FALSE; }
return m_pfnSHGetPathFromIDList(pidl, pszPath); }
//+----------------------------------------------------------------------------
//
// Function: CShellDll::ShellGetMalloc
//
// Synopsis: Wrapper function for SHGetMalloc.
//
// Arguments: Please see the api definition for SHGetMalloc
//
// Returns: HRESULT - Standard COM Error Codes
//
// History: quintinb Created 5/21/99
//
//+----------------------------------------------------------------------------
HRESULT CShellDll::ShellGetMalloc(LPMALLOC * ppMalloc) { if (!Load()) { return E_FAIL; }
return m_pfnSHGetMalloc(ppMalloc); }
|