CmDynLib.cpp 2.7 KB

1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586878889909192939495969798
  1. #include "CmDynLib.h"
  2. #include "CmException.h"
  3. #if CM_PLATFORM == CM_PLATFORM_WIN32
  4. # define WIN32_LEAN_AND_MEAN
  5. # if !defined(NOMINMAX) && defined(_MSC_VER)
  6. # define NOMINMAX // required to stop windows.h messing up std::min
  7. # endif
  8. # include <windows.h>
  9. #endif
  10. #if CM_PLATFORM == CM_PLATFORM_APPLE
  11. # include "macUtils.h"
  12. # include <dlfcn.h>
  13. #endif
  14. namespace CamelotFramework
  15. {
  16. DynLib::DynLib( const String& name )
  17. {
  18. mName = name;
  19. m_hInst = NULL;
  20. }
  21. DynLib::~DynLib()
  22. {
  23. }
  24. void DynLib::load()
  25. {
  26. String name = mName;
  27. #if CM_PLATFORM == CM_PLATFORM_LINUX
  28. // dlopen() does not add .so to the filename, like windows does for .dll
  29. if (name.substr(name.length() - 3, 3) != ".so")
  30. name += ".so";
  31. #elif CM_PLATFORM == CM_PLATFORM_APPLE
  32. // dlopen() does not add .dylib to the filename, like windows does for .dll
  33. if (name.substr(name.length() - 6, 6) != ".dylib")
  34. name += ".dylib";
  35. #elif CM_PLATFORM == CM_PLATFORM_WIN32
  36. // Although LoadLibraryEx will add .dll itself when you only specify the library name,
  37. // if you include a relative path then it does not. So, add it to be sure.
  38. if (name.substr(name.length() - 4, 4) != ".dll")
  39. name += ".dll";
  40. #endif
  41. m_hInst = (DYNLIB_HANDLE)DYNLIB_LOAD( name.c_str() );
  42. if( !m_hInst )
  43. {
  44. CM_EXCEPT(InternalErrorException,
  45. "Could not load dynamic library " + mName +
  46. ". System Error: " + dynlibError());
  47. }
  48. }
  49. void DynLib::unload()
  50. {
  51. if( DYNLIB_UNLOAD( m_hInst ) )
  52. {
  53. CM_EXCEPT(InternalErrorException,
  54. "Could not unload dynamic library " + mName +
  55. ". System Error: " + dynlibError());
  56. }
  57. }
  58. void* DynLib::getSymbol( const String& strName ) const throw()
  59. {
  60. return (void*)DYNLIB_GETSYM( m_hInst, strName.c_str() );
  61. }
  62. String DynLib::dynlibError( void )
  63. {
  64. #if CM_PLATFORM == CM_PLATFORM_WIN32
  65. LPVOID lpMsgBuf;
  66. FormatMessage(
  67. FORMAT_MESSAGE_ALLOCATE_BUFFER |
  68. FORMAT_MESSAGE_FROM_SYSTEM |
  69. FORMAT_MESSAGE_IGNORE_INSERTS,
  70. NULL,
  71. GetLastError(),
  72. MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT),
  73. (LPTSTR) &lpMsgBuf,
  74. 0,
  75. NULL
  76. );
  77. String ret = (char*)lpMsgBuf;
  78. // Free the buffer.
  79. LocalFree( lpMsgBuf );
  80. return ret;
  81. #elif CM_PLATFORM == CM_PLATFORM_LINUX || CM_PLATFORM == CM_PLATFORM_APPLE
  82. return String(dlerror());
  83. #else
  84. return String("");
  85. #endif
  86. }
  87. }