mirror of
https://gitlab.com/hashborgir/d2tweaks-rnd2k.git
synced 2024-11-30 12:45:58 +00:00
184 lines
4.9 KiB
C++
184 lines
4.9 KiB
C++
#pragma once
|
|
|
|
#include <cstdint>
|
|
#include <Windows.h>
|
|
|
|
namespace details {
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_cdecl_ {
|
|
void* m_function_ptr;
|
|
public:
|
|
explicit wrap_func_cdecl_(uintptr_t ptr, void* base) {
|
|
m_function_ptr = static_cast<char*>(base) + ptr;
|
|
}
|
|
|
|
TRet operator()(Args... args) {
|
|
return reinterpret_cast<TRet(__cdecl*)(Args...)>(m_function_ptr)(args...);
|
|
}
|
|
};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_std_ {
|
|
void* m_function_ptr;
|
|
public:
|
|
explicit wrap_func_std_(uintptr_t ptr, void* base) {
|
|
m_function_ptr = static_cast<char*>(base) + ptr;
|
|
}
|
|
|
|
TRet operator()(Args... args) {
|
|
return reinterpret_cast<TRet(__stdcall*)(Args...)>(m_function_ptr)(args...);
|
|
}
|
|
};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_cdecl_import_ {
|
|
void* m_base;
|
|
void* m_function_ptr;
|
|
uint32_t m_ordinal;
|
|
public:
|
|
explicit wrap_func_cdecl_import_(uint32_t ordinal, void* base) {
|
|
m_base = base;
|
|
m_function_ptr = nullptr;
|
|
m_ordinal = ordinal;
|
|
}
|
|
|
|
TRet operator()(Args... args) {
|
|
if (!m_function_ptr) {
|
|
m_function_ptr = reinterpret_cast<decltype(m_function_ptr)>(GetProcAddress(reinterpret_cast<HMODULE>(m_base),
|
|
reinterpret_cast<LPCSTR>(m_ordinal)));
|
|
}
|
|
|
|
return reinterpret_cast<TRet(__cdecl*)(Args...)>(m_function_ptr)(args...);
|
|
}
|
|
};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_std_import_ {
|
|
void* m_base;
|
|
void* m_function_ptr;
|
|
uint32_t m_ordinal;
|
|
public:
|
|
explicit wrap_func_std_import_(uint32_t ordinal, void* base) {
|
|
m_base = base;
|
|
m_function_ptr = nullptr;
|
|
m_ordinal = ordinal;
|
|
}
|
|
|
|
TRet operator()(Args... args) {
|
|
if (!m_function_ptr) {
|
|
m_function_ptr = reinterpret_cast<decltype(m_function_ptr)>(GetProcAddress(reinterpret_cast<HMODULE>(m_base),
|
|
reinterpret_cast<LPCSTR>(m_ordinal)));
|
|
}
|
|
|
|
return reinterpret_cast<TRet(__stdcall*)(Args...)>(m_function_ptr)(args...);
|
|
}
|
|
};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_fast_import_ {
|
|
void* m_base;
|
|
void* m_function_ptr;
|
|
uint32_t m_ordinal;
|
|
public:
|
|
explicit wrap_func_fast_import_(uint32_t ordinal, void* base) {
|
|
m_base = base;
|
|
m_function_ptr = nullptr;
|
|
m_ordinal = ordinal;
|
|
}
|
|
|
|
TRet operator()(Args... args) {
|
|
if (!m_function_ptr) {
|
|
m_function_ptr = reinterpret_cast<decltype(m_function_ptr)>(GetProcAddress(reinterpret_cast<HMODULE>(m_base),
|
|
reinterpret_cast<LPCSTR>(m_ordinal)));
|
|
}
|
|
|
|
return reinterpret_cast<TRet(__fastcall*)(Args...)>(m_function_ptr)(args...);
|
|
}
|
|
};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_fast_ {
|
|
void* m_function_ptr;
|
|
public:
|
|
explicit wrap_func_fast_(uintptr_t ptr, void* base) {
|
|
m_function_ptr = static_cast<char*>(base) + ptr;
|
|
}
|
|
|
|
TRet operator()(Args... args) {
|
|
return reinterpret_cast<TRet(__fastcall*)(Args...)>(m_function_ptr)(args...);
|
|
}
|
|
};
|
|
}
|
|
|
|
template<typename TRet>
|
|
class wrap_func_cdecl {};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_cdecl<TRet(Args...)> : public details::wrap_func_cdecl_<TRet, Args...> {
|
|
public:
|
|
wrap_func_cdecl(uintptr_t ptr, void* base) : wrap_func_cdecl_(ptr, base) {};
|
|
};
|
|
|
|
template<typename TRet>
|
|
class wrap_func_cdecl_import {};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_cdecl_import<TRet(Args...)> : public details::wrap_func_cdecl_import_<TRet, Args...> {
|
|
public:
|
|
wrap_func_cdecl_import(uint32_t ordinal, void* base) : wrap_func_cdecl_import_(ordinal, base) {};
|
|
};
|
|
|
|
template<typename TRet>
|
|
class wrap_func_std {};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_std<TRet(Args...)> : public details::wrap_func_std_<TRet, Args...> {
|
|
public:
|
|
wrap_func_std(uintptr_t ptr, void* base) : wrap_func_std_(ptr, base) {};
|
|
};
|
|
|
|
template<typename TRet>
|
|
class wrap_func_std_import {};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_std_import<TRet(Args...)> : public details::wrap_func_std_import_<TRet, Args...> {
|
|
public:
|
|
wrap_func_std_import(uint32_t ordinal, void* base) : wrap_func_std_import_(ordinal, base) {};
|
|
};
|
|
|
|
template<typename TRet>
|
|
class wrap_func_fast_import {};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_fast_import<TRet(Args...)> : public details::wrap_func_fast_import_<TRet, Args...> {
|
|
public:
|
|
wrap_func_fast_import(uint32_t ordinal, void* base) : wrap_func_fast_import_(ordinal, base) {};
|
|
};
|
|
|
|
template<typename TRet>
|
|
class wrap_func_fast {};
|
|
|
|
template<typename TRet, typename... Args>
|
|
class wrap_func_fast<TRet(Args...)> : public details::wrap_func_fast_<TRet, Args...> {
|
|
public:
|
|
wrap_func_fast(uintptr_t ptr, void* base) : wrap_func_fast_(ptr, base) {};
|
|
};
|
|
|
|
template<typename TType>
|
|
class wrap_value {
|
|
TType* m_value;
|
|
public:
|
|
wrap_value(uintptr_t ptr, void* base) {
|
|
// Fuck off, I'm gonna cast it in C-style because of templates
|
|
// ReSharper disable once CppCStyleCast
|
|
m_value = (TType*)(static_cast<char*>(base) + ptr);
|
|
}
|
|
|
|
operator void* () const {
|
|
return m_value;
|
|
}
|
|
|
|
operator TType* () const {
|
|
return m_value;
|
|
}
|
|
}; |