X-Git-Url: https://git.saurik.com/wxWidgets.git/blobdiff_plain/80fdcdb90ef779185492dab676d461fc34933312..739c5499fcab1c165b8dd0591c9fd9e2329b3cf9:/src/msw/dlmsw.cpp diff --git a/src/msw/dlmsw.cpp b/src/msw/dlmsw.cpp index cdff7387ab..0bb76d72db 100644 --- a/src/msw/dlmsw.cpp +++ b/src/msw/dlmsw.cpp @@ -27,6 +27,7 @@ #include "wx/msw/private.h" #include "wx/msw/debughlp.h" +#include "wx/filename.h" const wxString wxDynamicLibrary::ms_dllext(wxT(".dll")); @@ -224,13 +225,62 @@ wxDllType wxDynamicLibrary::GetProgramHandle() // loading/unloading DLLs // ---------------------------------------------------------------------------- +#ifndef MAX_PATH + #define MAX_PATH 260 // from VC++ headers +#endif + /* static */ wxDllType wxDynamicLibrary::RawLoad(const wxString& libname, int flags) { - return flags & wxDL_GET_LOADED - ? ::GetModuleHandle(libname.t_str()) - : ::LoadLibrary(libname.t_str()); + if (flags & wxDL_GET_LOADED) + return ::GetModuleHandle(libname.t_str()); + + // Explicitly look in the same path as where the main wx HINSTANCE module + // is located (usually the executable or the DLL that uses wx). Normally + // this is automatically part of the default search path but in some cases + // it may not be, such as when the wxPython extension modules need to load + // a DLL, but the intperpreter executable is located elsewhere. Doing + // this allows us to always be able to dynamically load a DLL that is + // located at the same place as the wx modules. + wxString modpath, path; + ::GetModuleFileName(wxGetInstance(), + wxStringBuffer(modpath, MAX_PATH+1), + MAX_PATH); + + wxFileName::SplitPath(modpath, &path, NULL, NULL); + + typedef BOOL (WINAPI *SetDllDirectory_t)(LPCTSTR lpPathName); + + static SetDllDirectory_t s_pfnSetDllDirectory = (SetDllDirectory_t) -1; + + if ( s_pfnSetDllDirectory == (SetDllDirectory_t) -1 ) + { + /* + Should wxLoadedDLL ever not be used here (or rather, the + wxDL_GET_LOADED flag isn't used), infinite recursion will take + place (unless s_pfnSetDllDirectory is set to NULL here right + before loading the DLL). + */ + wxLoadedDLL dllKernel("kernel32.dll"); + + wxDL_INIT_FUNC_AW(s_pfn, SetDllDirectory, dllKernel); + } + + if (s_pfnSetDllDirectory) + { + s_pfnSetDllDirectory(path.t_str()); + } + + wxDllType handle = ::LoadLibrary(libname.t_str()); + + // reset the search path + if (s_pfnSetDllDirectory) + { + s_pfnSetDllDirectory(NULL); + } + + return handle; } /* static */