17 #ifndef DISTRHO_LIBRARY_UTILS_HPP_INCLUDED 
   18 #define DISTRHO_LIBRARY_UTILS_HPP_INCLUDED 
   20 #include "../DistrhoUtils.hpp" 
   22 #ifdef DISTRHO_OS_WINDOWS 
   23 # include <winsock2.h> 
   25 typedef HMODULE lib_t;
 
   39 lib_t lib_open(
const char* 
const filename) noexcept
 
   41     DISTRHO_SAFE_ASSERT_RETURN(filename != 
nullptr && filename[0] != 
'\0', 
nullptr);
 
   44 #ifdef DISTRHO_OS_WINDOWS 
   45         return ::LoadLibraryA(filename);
 
   47         return ::dlopen(filename, RTLD_NOW|RTLD_LOCAL);
 
   49     } DISTRHO_SAFE_EXCEPTION_RETURN(
"lib_open", 
nullptr);
 
   57 bool lib_close(
const lib_t lib) noexcept
 
   59     DISTRHO_SAFE_ASSERT_RETURN(lib != 
nullptr, 
false);
 
   62 #ifdef DISTRHO_OS_WINDOWS 
   63         return ::FreeLibrary(lib);
 
   65         return (::dlclose(lib) == 0);
 
   67     } DISTRHO_SAFE_EXCEPTION_RETURN(
"lib_close", 
false);
 
   74 template<
typename Func>
 
   76 Func lib_symbol(
const lib_t lib, 
const char* 
const symbol) noexcept
 
   78     DISTRHO_SAFE_ASSERT_RETURN(lib != 
nullptr, 
nullptr);
 
   79     DISTRHO_SAFE_ASSERT_RETURN(symbol != 
nullptr && symbol[0] != 
'\0', 
nullptr);
 
   82 #ifdef DISTRHO_OS_WINDOWS 
   83 # if defined(__GNUC__) && (__GNUC__ >= 9) 
   84 #  pragma GCC diagnostic push 
   85 #  pragma GCC diagnostic ignored "-Wcast-function-type" 
   87         return (Func)::GetProcAddress(lib, symbol);
 
   88 # if defined(__GNUC__) && (__GNUC__ >= 9) 
   89 #  pragma GCC diagnostic pop 
   92         return (Func)(uintptr_t)::dlsym(lib, symbol);
 
   94     } DISTRHO_SAFE_EXCEPTION_RETURN(
"lib_symbol", 
nullptr);
 
  102 const char* lib_error(
const char* 
const filename) noexcept
 
  104     DISTRHO_SAFE_ASSERT_RETURN(filename != 
nullptr && filename[0] != 
'\0', 
nullptr);
 
  106 #ifdef DISTRHO_OS_WINDOWS 
  107     static char libError[2048+1];
 
  108     std::memset(libError, 0, 
sizeof(libError));
 
  111         const DWORD winErrorCode  = ::GetLastError();
 
  112         const int   winErrorFlags = FORMAT_MESSAGE_ALLOCATE_BUFFER|FORMAT_MESSAGE_FROM_SYSTEM|FORMAT_MESSAGE_IGNORE_INSERTS;
 
  113         LPVOID      winErrorString;
 
  115         ::FormatMessage(winErrorFlags, 
nullptr, winErrorCode, MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), (LPTSTR)&winErrorString, 0, 
nullptr);
 
  117         std::snprintf(libError, 2048, 
"%s: error code %li: %s", filename, winErrorCode, (
const char*)winErrorString);
 
  118         ::LocalFree(winErrorString);
 
  119     } DISTRHO_SAFE_EXCEPTION(
"lib_error");
 
  121     return (libError[0] != 
'\0') ? libError : 
nullptr;
 
  129 #endif // DISTRHO_LIBRARY_UTILS_HPP_INCLUDED