p7zip-rar/CPP/7zip/Compress/Lzham/include/lzham_dynamic_lib.h

157 lines
4.1 KiB
C
Raw Normal View History

2017-10-11 12:40:22 +02:00
#pragma once
#define LZHAM_DYNAMIC_LIB 1
#include "lzham.h"
#ifdef _XBOX
#define LZHAM_DLL_FILENAME "lzham_x360.dll"
#define LZHAM_DEBUG_DLL_FILENAME "lzham_x360D.dll"
#else
// FIXME: This stuff should probably be moved to another header.
#if LZHAM_64BIT
#define LZHAM_DLL_FILENAME "lzham_x64.dll"
#define LZHAM_DEBUG_DLL_FILENAME "lzham_x64D.dll"
#else
#define LZHAM_DLL_FILENAME "lzham_x86.dll"
#define LZHAM_DEBUG_DLL_FILENAME "lzham_x86D.dll"
#endif
#endif
#ifdef __cplusplus
// Simple helper class that demonstrates how to dynamically load the LZHAM DLL.
// The load() method loads the DLL, then initializes the member function pointers in ilzham by calling GetProcAddress() on all exported API's defined in lzham_exports.inc.
class lzham_dll_loader : public ilzham
{
lzham_dll_loader(const lzham_dll_loader &other);
lzham_dll_loader& operator= (const lzham_dll_loader &rhs);
public:
lzham_dll_loader() : ilzham(), m_handle(NULL), m_win32_error(S_OK)
{
}
virtual ~lzham_dll_loader()
{
unload();
}
enum
{
cErrorMissingExport = MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x201),
cErrorUnsupportedDLLVersion = MAKE_HRESULT(SEVERITY_ERROR, FACILITY_ITF, 0x202),
};
// Assumes LZHAM DLL is in the same path as the executable.
#if defined(_XBOX) || defined(_MSC_VER)
static void create_module_path(char *pModulePath, int size_in_chars, bool debug_dll)
{
#ifdef _XBOX
char *buf = "D:\\unused.xex";
#else
char buf[MAX_PATH];
GetModuleFileNameA(NULL, buf, sizeof(buf));
#endif
char drive_buf[_MAX_DRIVE], dir_buf[_MAX_DIR], filename_buf[_MAX_FNAME], ext_buf[_MAX_EXT];
_splitpath_s(buf, drive_buf, _MAX_DRIVE, dir_buf, _MAX_DIR, NULL, 0, NULL, 0);
_splitpath_s(debug_dll ? LZHAM_DEBUG_DLL_FILENAME : LZHAM_DLL_FILENAME, NULL, 0, NULL, 0, filename_buf, _MAX_FNAME, ext_buf, _MAX_EXT);
_makepath_s(pModulePath, size_in_chars, drive_buf, dir_buf, filename_buf, ext_buf);
}
#else
static void create_module_path(char *pModulePath, int size_in_chars, bool debug_dll)
{
strcpy(pModulePath, debug_dll ? LZHAM_DEBUG_DLL_FILENAME : LZHAM_DLL_FILENAME);
}
#endif
virtual bool load()
{
HRESULT hres = load(NULL);
return S_OK == hres;
}
HRESULT load(const char* pModulePath)
{
unload();
char buf[MAX_PATH];
if (!pModulePath)
{
create_module_path(buf, sizeof(buf), false);
pModulePath = buf;
}
m_win32_error = S_OK;
m_handle = LoadLibraryA(pModulePath);
if (NULL == m_handle)
{
m_win32_error = HRESULT_FROM_WIN32(GetLastError());
return m_win32_error;
}
struct
{
const char* pName;
void** pFunc_ptr;
}
funcs[] =
{
#define LZHAM_DLL_FUNC_NAME(x) { #x, (void**)&x },
#include "lzham_exports.inc"
#undef LZHAM_DLL_FUNC_NAME
};
const int cNumFuncs = sizeof(funcs) / sizeof(funcs[0]);
for (int i = 0; i < cNumFuncs; i++)
{
#ifdef _XBOX
if ((*funcs[i].pFunc_ptr = GetProcAddress(m_handle, (LPCSTR)(i + 1))) == NULL)
#else
if ((*funcs[i].pFunc_ptr = (void*)GetProcAddress(m_handle, funcs[i].pName)) == NULL)
#endif
{
unload();
m_win32_error = cErrorMissingExport;
return m_win32_error;
}
}
int dll_ver = lzham_get_version();
// Ensure DLL's major version is the expected version.
if ((dll_ver >> 8U) != (LZHAM_DLL_VERSION >> 8U))
{
unload();
m_win32_error = cErrorUnsupportedDLLVersion;
return m_win32_error;
}
return S_OK;
}
virtual void unload()
{
if (m_handle)
{
FreeLibrary(m_handle);
m_handle = NULL;
}
clear();
m_win32_error = S_OK;
}
virtual bool is_loaded() { return m_handle != NULL; }
HRESULT get_last_win32_error() { return m_win32_error; }
private:
HMODULE m_handle;
HRESULT m_win32_error;
};
#endif // #ifdef __cplusplus