As previously discussed here, I'm trying to find a workaround for the LNK2019 issue that arises when building a static library which utilizes C++ templates, and separating the source from the header to keep the code private from other projects. I believe I've nearly come to a working conclusion (for my particular situation), but I'm not entirely sure if this is the correct/best way to go about it and was wondering if anyone has any suggestions, improvements/comments to add?
The goal is to do some type checking to see if the template's signature matches the target prototype function's signature, do some private processing, and return whether or not it was sucessful. NOTE that I have removed SdkHookMgr.h
and SdkHookMgr.cpp
from the prior version of the solution in the above link, and merged everything back into SdkLib.h
and SdkLib.cpp
, into a static class for a bit of clarity.
SdkLib.h:
#include <typeinfo>
#ifdef MY_EXPORTS
# define MYDECL __declspec(dllexport)
#else
# define MYDECL
#endif
// Prototypes
typedef HMODULE (WINAPI *HookLoadLibraryA)( LPCSTR lpFileName );
//...
class CHook;
class CHookManager;
MYDECL BOOL WINAPI ValidateHook( CHook *hook );
class CHook
{
public:
CHook() : m_type(NULL), m_target(NULL), m_result(FALSE) {};
CHook( const char *type, PVOID target ) : m_type(type), m_target(target) {
m_result = ValidateHook(this);
};
const char *m_type;
PVOID m_target;
BOOL m_result;
};
class CHookManager
{
public:
template <typename HookFunction> static BOOL Hook(HookFunction target)
{
const type_info& type = typeid(HookFunction);
CHook *hook = new CHook( type.name(), target );
return hook->m_result;
}
};
SdkLib.cpp:
#include <SdkLib.h>
IDXDECL BOOL WINAPI ValidateHook( CHook *hook )
{
// Do type checking, private processing, etc here...
return TRUE;
}
DemoDLL.cpp:
#include <SdkLib.h>
HMODULE WINAPI Hooked_LoadLibraryA( LPCSTR lpFileName )
{
DebugBreak();
}
// The function that starts the rollercoaster.
// - Syntax: Hook< prototype >( target )
if!(CHookManager::Hook<HookLoadLibraryA>(Hooked_LoadLibraryA))
cout << "Failed to create hook for LoadLibraryA!" << endl;