static wxString GetPluginsDirectory();
+#ifdef __WXMSW__
+ // return the handle (HMODULE/HINSTANCE) of the DLL with the given name
+ // and/or containing the specified address: for XP and later systems only
+ // the address is used and the name is ignored but for the previous systems
+ // only the name (which may be either a full path to the DLL or just its
+ // base name, possibly even without extension) is used
+ //
+ // the returned handle reference count is not incremented so it doesn't
+ // need to be freed using FreeLibrary() but it also means that it can
+ // become invalid if the DLL is unloaded
+ static HINSTANCE MSWGetModuleHandle(const char *name, void *addr);
+#endif // __WXMSW__
+
protected:
// common part of GetSymbol() and HasSymbol()
void *DoGetSymbol(const wxString& name, bool *success = 0) const;
#endif
#include "wx/app.h"
+#include "wx/dynlib.h"
#include "wx/frame.h"
#include "wx/panel.h"
#include "wx/sizer.h"
// at this point and won't release it until we signal it.
// We need to pass correct HINSTANCE to wxEntry() and the right value is
- // HINSTANCE of this DLL, not of the main .exe.
- //
- // This method of obtaining DLL's instance handle requires at least
- // Windows XP/2003. We could also implement DllMain() and remember it from
- // there, that would work on older systems too.
- HINSTANCE hInstance;
- int ret = GetModuleHandleEx(GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS,
- (LPCTSTR)&MyAppLauncher,
- &hInstance);
- if ( ret == 0 )
+ // HINSTANCE of this DLL, not of the main .exe, use this MSW-specific wx
+ // function to get it. Notice that under Windows XP and later the name is
+ // not needed/used as we retrieve the DLL handle from an address inside it
+ // but you do need to use the correct name for this code to work with older
+ // systems as well.
+ const HINSTANCE
+ hInstance = wxDynamicLibrary::MSWGetModuleHandle("my_dll",
+ &gs_wxMainThread);
+ if ( !hInstance )
return 0; // failed to get DLL's handle
// IMPLEMENT_WXWIN_MAIN does this as the first thing
EnumModulesProc(NameStr_t name, DWORD_32_64 base, ULONG size, void *data);
};
-// ----------------------------------------------------------------------------
-// private functions
-// ----------------------------------------------------------------------------
-
-// return the module handle for the given base name
-static
-HMODULE wxGetModuleHandle(const char *name, void *addr)
-{
- // we want to use GetModuleHandleEx() instead of usual GetModuleHandle()
- // because the former works correctly for comctl32.dll while the latter
- // returns NULL when comctl32.dll version 6 is used under XP (note that
- // GetModuleHandleEx() is only available under XP and later, coincidence?)
-
- // check if we can use GetModuleHandleEx
- typedef BOOL (WINAPI *GetModuleHandleEx_t)(DWORD, LPCSTR, HMODULE *);
-
- static const GetModuleHandleEx_t INVALID_FUNC_PTR = (GetModuleHandleEx_t)-1;
-
- static GetModuleHandleEx_t s_pfnGetModuleHandleEx = INVALID_FUNC_PTR;
- if ( s_pfnGetModuleHandleEx == INVALID_FUNC_PTR )
- {
- wxDynamicLibrary dll(wxT("kernel32.dll"), wxDL_VERBATIM);
- s_pfnGetModuleHandleEx =
- (GetModuleHandleEx_t)dll.RawGetSymbol(wxT("GetModuleHandleExA"));
-
- // dll object can be destroyed, kernel32.dll won't be unloaded anyhow
- }
-
- // get module handle from its address
- if ( s_pfnGetModuleHandleEx )
- {
- // flags are GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT |
- // GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS
- HMODULE hmod;
- if ( s_pfnGetModuleHandleEx(6, (char *)addr, &hmod) && hmod )
- return hmod;
- }
-
- // Windows CE only has Unicode API, so even we have an ANSI string here, we
- // still need to use GetModuleHandleW() there
-#ifdef __WXWINCE__
- return ::GetModuleHandleW(wxConvLibc.cMB2WC(name).data());
-#else
- return ::GetModuleHandleA((char *)name);
-#endif
-}
-
// ============================================================================
// wxVersionDLL implementation
// ============================================================================
details->m_length = size;
// to get the version, we first need the full path
- HMODULE hmod = wxGetModuleHandle(name, details->m_address);
+ const HMODULE
+ hmod = wxDynamicLibrary::MSWGetModuleHandle(name, details->m_address);
if ( hmod )
{
wxString fullname = wxGetFullModuleName(hmod);
return dlls;
}
+/* static */
+HMODULE wxDynamicLibrary::MSWGetModuleHandle(const char *name, void *addr)
+{
+ // we want to use GetModuleHandleEx() instead of usual GetModuleHandle()
+ // because the former works correctly for comctl32.dll while the latter
+ // returns NULL when comctl32.dll version 6 is used under XP (note that
+ // GetModuleHandleEx() is only available under XP and later, coincidence?)
+
+ // check if we can use GetModuleHandleEx
+ typedef BOOL (WINAPI *GetModuleHandleEx_t)(DWORD, LPCSTR, HMODULE *);
+
+ static const GetModuleHandleEx_t INVALID_FUNC_PTR = (GetModuleHandleEx_t)-1;
+
+ static GetModuleHandleEx_t s_pfnGetModuleHandleEx = INVALID_FUNC_PTR;
+ if ( s_pfnGetModuleHandleEx == INVALID_FUNC_PTR )
+ {
+ wxDynamicLibrary dll(wxT("kernel32.dll"), wxDL_VERBATIM);
+ s_pfnGetModuleHandleEx =
+ (GetModuleHandleEx_t)dll.RawGetSymbol(wxT("GetModuleHandleExA"));
+
+ // dll object can be destroyed, kernel32.dll won't be unloaded anyhow
+ }
+
+ // get module handle from its address
+ if ( s_pfnGetModuleHandleEx )
+ {
+ // flags are GET_MODULE_HANDLE_EX_FLAG_UNCHANGED_REFCOUNT |
+ // GET_MODULE_HANDLE_EX_FLAG_FROM_ADDRESS
+ HMODULE hmod;
+ if ( s_pfnGetModuleHandleEx(6, (char *)addr, &hmod) && hmod )
+ return hmod;
+ }
+
+ // Windows CE only has Unicode API, so even we have an ANSI string here, we
+ // still need to use GetModuleHandleW() there
+#ifdef __WXWINCE__
+ return ::GetModuleHandleW(wxConvLibc.cMB2WC(name).data());
+#else
+ return ::GetModuleHandleA((char *)name);
+#endif
+}
+
#endif // wxUSE_DYNLIB_CLASS