mirror of
https://github.com/holub/mame
synced 2025-06-07 13:23:50 +03:00
Introduce dynamic_module
This is a central cross-platform facility to dynamically bind functions from shared libraries. Updated all OSD modules to use it.
This commit is contained in:
parent
ea1b66f146
commit
58dc78b6eb
@ -154,8 +154,6 @@ project ("osd_" .. _OPTIONS["osd"])
|
|||||||
}
|
}
|
||||||
|
|
||||||
files {
|
files {
|
||||||
MAME_DIR .. "src/osd/modules/render/d3d/d3d9intf.cpp",
|
|
||||||
MAME_DIR .. "src/osd/modules/render/d3d/d3dintf.h",
|
|
||||||
MAME_DIR .. "src/osd/modules/render/d3d/d3dhlsl.cpp",
|
MAME_DIR .. "src/osd/modules/render/d3d/d3dhlsl.cpp",
|
||||||
MAME_DIR .. "src/osd/modules/render/d3d/d3dcomm.h",
|
MAME_DIR .. "src/osd/modules/render/d3d/d3dcomm.h",
|
||||||
MAME_DIR .. "src/osd/modules/render/d3d/d3dhlsl.h",
|
MAME_DIR .. "src/osd/modules/render/d3d/d3dhlsl.h",
|
||||||
|
@ -22,30 +22,21 @@
|
|||||||
|
|
||||||
#include <memory>
|
#include <memory>
|
||||||
#include <vector>
|
#include <vector>
|
||||||
|
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
#include <windows/winutil.h>
|
#include <windows/winutil.h>
|
||||||
|
|
||||||
template<typename _FunctionPtr>
|
// Typedefs for dynamically loaded functions
|
||||||
class dynamic_bind
|
typedef BOOL WINAPI (*StackWalk64_fn)(DWORD, HANDLE, HANDLE, LPSTACKFRAME64, PVOID, PREAD_PROCESS_MEMORY_ROUTINE64, PFUNCTION_TABLE_ACCESS_ROUTINE64, PGET_MODULE_BASE_ROUTINE64, PTRANSLATE_ADDRESS_ROUTINE64);
|
||||||
{
|
typedef BOOL WINAPI (*SymInitialize_fn)(HANDLE, LPCTSTR, BOOL);
|
||||||
public:
|
typedef PVOID WINAPI (*SymFunctionTableAccess64_fn)(HANDLE, DWORD64);
|
||||||
// constructor which looks up the function
|
typedef DWORD64 WINAPI (*SymGetModuleBase64_fn)(HANDLE, DWORD64);
|
||||||
dynamic_bind(const TCHAR *dll, const char *symbol)
|
typedef BOOL WINAPI (*SymFromAddr_fn)(HANDLE, DWORD64, PDWORD64, PSYMBOL_INFO);
|
||||||
: m_function(nullptr)
|
typedef BOOL WINAPI (*SymGetLineFromAddr64_fn)(HANDLE, DWORD64, PDWORD, PIMAGEHLP_LINE64);
|
||||||
{
|
typedef PIMAGE_SECTION_HEADER WINAPI (*ImageRvaToSection_fn)(PIMAGE_NT_HEADERS, PVOID, ULONG);
|
||||||
HMODULE module = LoadLibrary(dll);
|
typedef PIMAGE_NT_HEADERS WINAPI (*ImageNtHeader_fn)(PVOID);
|
||||||
if (module != nullptr)
|
typedef VOID WINAPI (*RtlCaptureContext_fn)(PCONTEXT);
|
||||||
m_function = reinterpret_cast<_FunctionPtr>(GetProcAddress(module, symbol));
|
|
||||||
}
|
|
||||||
|
|
||||||
// bool to test if the function is nullptr or not
|
|
||||||
operator bool() const { return (m_function != nullptr); }
|
|
||||||
|
|
||||||
// dereference to get the underlying pointer
|
|
||||||
_FunctionPtr operator *() const { return m_function; }
|
|
||||||
|
|
||||||
private:
|
|
||||||
_FunctionPtr m_function;
|
|
||||||
};
|
|
||||||
|
|
||||||
class stack_walker
|
class stack_walker
|
||||||
{
|
{
|
||||||
@ -67,12 +58,14 @@ private:
|
|||||||
CONTEXT m_context;
|
CONTEXT m_context;
|
||||||
bool m_first;
|
bool m_first;
|
||||||
|
|
||||||
dynamic_bind<BOOL(WINAPI *)(DWORD, HANDLE, HANDLE, LPSTACKFRAME64, PVOID, PREAD_PROCESS_MEMORY_ROUTINE64, PFUNCTION_TABLE_ACCESS_ROUTINE64, PGET_MODULE_BASE_ROUTINE64, PTRANSLATE_ADDRESS_ROUTINE64)>
|
osd::dynamic_module::ptr m_dbghelp_dll;
|
||||||
m_stack_walk_64;
|
osd::dynamic_module::ptr m_kernel32_dll;
|
||||||
dynamic_bind<BOOL(WINAPI *)(HANDLE, LPCTSTR, BOOL)> m_sym_initialize;
|
|
||||||
dynamic_bind<PVOID(WINAPI *)(HANDLE, DWORD64)> m_sym_function_table_access_64;
|
StackWalk64_fn m_stack_walk_64;
|
||||||
dynamic_bind<DWORD64(WINAPI *)(HANDLE, DWORD64)> m_sym_get_module_base_64;
|
SymInitialize_fn m_sym_initialize;
|
||||||
dynamic_bind<VOID(WINAPI *)(PCONTEXT)> m_rtl_capture_context;
|
SymFunctionTableAccess64_fn m_sym_function_table_access_64;
|
||||||
|
SymGetModuleBase64_fn m_sym_get_module_base_64;
|
||||||
|
RtlCaptureContext_fn m_rtl_capture_context;
|
||||||
|
|
||||||
static bool s_initialized;
|
static bool s_initialized;
|
||||||
};
|
};
|
||||||
@ -126,8 +119,10 @@ private:
|
|||||||
FPTR m_last_base;
|
FPTR m_last_base;
|
||||||
FPTR m_text_base;
|
FPTR m_text_base;
|
||||||
|
|
||||||
dynamic_bind<BOOL(WINAPI *)(HANDLE, DWORD64, PDWORD64, PSYMBOL_INFO)> m_sym_from_addr;
|
osd::dynamic_module::ptr m_dbghelp_dll;
|
||||||
dynamic_bind<BOOL(WINAPI *)(HANDLE, DWORD64, PDWORD, PIMAGEHLP_LINE64)> m_sym_get_line_from_addr_64;
|
|
||||||
|
SymFromAddr_fn m_sym_from_addr;
|
||||||
|
SymGetLineFromAddr64_fn m_sym_get_line_from_addr_64;
|
||||||
};
|
};
|
||||||
|
|
||||||
class sampling_profiler
|
class sampling_profiler
|
||||||
@ -176,17 +171,21 @@ bool stack_walker::s_initialized = false;
|
|||||||
stack_walker::stack_walker()
|
stack_walker::stack_walker()
|
||||||
: m_process(GetCurrentProcess()),
|
: m_process(GetCurrentProcess()),
|
||||||
m_thread(GetCurrentThread()),
|
m_thread(GetCurrentThread()),
|
||||||
m_first(true),
|
m_first(true)
|
||||||
m_stack_walk_64(TEXT("dbghelp.dll"), "StackWalk64"),
|
|
||||||
m_sym_initialize(TEXT("dbghelp.dll"), "SymInitialize"),
|
|
||||||
m_sym_function_table_access_64(TEXT("dbghelp.dll"), "SymFunctionTableAccess64"),
|
|
||||||
m_sym_get_module_base_64(TEXT("dbghelp.dll"), "SymGetModuleBase64"),
|
|
||||||
m_rtl_capture_context(TEXT("kernel32.dll"), "RtlCaptureContext")
|
|
||||||
{
|
{
|
||||||
// zap the structs
|
// zap the structs
|
||||||
memset(&m_stackframe, 0, sizeof(m_stackframe));
|
memset(&m_stackframe, 0, sizeof(m_stackframe));
|
||||||
memset(&m_context, 0, sizeof(m_context));
|
memset(&m_context, 0, sizeof(m_context));
|
||||||
|
|
||||||
|
m_dbghelp_dll = osd::dynamic_module::open({ "dbghelp.dll" });
|
||||||
|
m_kernel32_dll = osd::dynamic_module::open({ "kernel32.dll" });
|
||||||
|
|
||||||
|
m_stack_walk_64 = m_dbghelp_dll->bind<StackWalk64_fn>("StackWalk64");
|
||||||
|
m_sym_initialize = m_dbghelp_dll->bind<SymInitialize_fn>("SymInitialize");
|
||||||
|
m_sym_function_table_access_64 = m_dbghelp_dll->bind<SymFunctionTableAccess64_fn>("SymFunctionTableAccess64");
|
||||||
|
m_sym_get_module_base_64 = m_dbghelp_dll->bind<SymGetModuleBase64_fn>("SymGetModuleBase64");
|
||||||
|
m_rtl_capture_context = m_kernel32_dll->bind<RtlCaptureContext_fn>("RtlCaptureContext");
|
||||||
|
|
||||||
// initialize the symbols
|
// initialize the symbols
|
||||||
if (!s_initialized && m_sym_initialize && m_stack_walk_64 && m_sym_function_table_access_64 && m_sym_get_module_base_64)
|
if (!s_initialized && m_sym_initialize && m_stack_walk_64 && m_sym_function_table_access_64 && m_sym_get_module_base_64)
|
||||||
{
|
{
|
||||||
@ -294,9 +293,7 @@ symbol_manager::symbol_manager(const char *argv0)
|
|||||||
m_symfile(argv0),
|
m_symfile(argv0),
|
||||||
m_process(GetCurrentProcess()),
|
m_process(GetCurrentProcess()),
|
||||||
m_last_base(0),
|
m_last_base(0),
|
||||||
m_text_base(0),
|
m_text_base(0)
|
||||||
m_sym_from_addr(TEXT("dbghelp.dll"), "SymFromAddr"),
|
|
||||||
m_sym_get_line_from_addr_64(TEXT("dbghelp.dll"), "SymGetLineFromAddr64")
|
|
||||||
{
|
{
|
||||||
#ifdef __GNUC__
|
#ifdef __GNUC__
|
||||||
// compute the name of the mapfile
|
// compute the name of the mapfile
|
||||||
@ -317,6 +314,11 @@ symbol_manager::symbol_manager(const char *argv0)
|
|||||||
|
|
||||||
// expand the buffer to be decently large up front
|
// expand the buffer to be decently large up front
|
||||||
m_buffer = string_format("%500s", "");
|
m_buffer = string_format("%500s", "");
|
||||||
|
|
||||||
|
m_dbghelp_dll = osd::dynamic_module::open({ "dbghelp.dll" });
|
||||||
|
|
||||||
|
m_sym_from_addr = m_dbghelp_dll->bind<SymFromAddr_fn>("SymFromAddr");
|
||||||
|
m_sym_get_line_from_addr_64 = m_dbghelp_dll->bind<SymGetLineFromAddr64_fn>("SymGetLineFromAddr64");
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -603,8 +605,10 @@ void symbol_manager::format_symbol(const char *name, UINT32 displacement, const
|
|||||||
|
|
||||||
FPTR symbol_manager::get_text_section_base()
|
FPTR symbol_manager::get_text_section_base()
|
||||||
{
|
{
|
||||||
dynamic_bind<PIMAGE_SECTION_HEADER(WINAPI *)(PIMAGE_NT_HEADERS, PVOID, ULONG)> image_rva_to_section(TEXT("dbghelp.dll"), "ImageRvaToSection");
|
osd::dynamic_module::ptr m_dbghelp_dll = osd::dynamic_module::open({ "dbghelp.dll" });
|
||||||
dynamic_bind<PIMAGE_NT_HEADERS(WINAPI *)(PVOID)> image_nt_header(TEXT("dbghelp.dll"), "ImageNtHeader");
|
|
||||||
|
ImageRvaToSection_fn image_rva_to_section = m_dbghelp_dll->bind<ImageRvaToSection_fn>("ImageRvaToSection");
|
||||||
|
ImageNtHeader_fn image_nt_header = m_dbghelp_dll->bind<ImageNtHeader_fn>("ImageNtHeader");
|
||||||
|
|
||||||
// start with the image base
|
// start with the image base
|
||||||
PVOID base = reinterpret_cast<PVOID>(GetModuleHandleUni());
|
PVOID base = reinterpret_cast<PVOID>(GetModuleHandleUni());
|
||||||
|
@ -7,6 +7,7 @@
|
|||||||
|
|
||||||
#include "font_module.h"
|
#include "font_module.h"
|
||||||
#include "modules/osdmodule.h"
|
#include "modules/osdmodule.h"
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
// We take dependencies on WRL client headers and
|
// We take dependencies on WRL client headers and
|
||||||
// we can only build with a high enough version
|
// we can only build with a high enough version
|
||||||
@ -78,8 +79,8 @@ struct osd_deleter
|
|||||||
typedef std::unique_ptr<char, osd_deleter> osd_utf8_ptr;
|
typedef std::unique_ptr<char, osd_deleter> osd_utf8_ptr;
|
||||||
|
|
||||||
// Typedefs for dynamically loaded functions
|
// Typedefs for dynamically loaded functions
|
||||||
typedef lazy_loaded_function_p4<HRESULT, D2D1_FACTORY_TYPE, REFIID, const D2D1_FACTORY_OPTIONS*, void**> d2d_create_factory_fn;
|
typedef HRESULT WINAPI (*d2d_create_factory_fn)(D2D1_FACTORY_TYPE, REFIID, const D2D1_FACTORY_OPTIONS *, void **);
|
||||||
typedef lazy_loaded_function_p3<HRESULT, DWRITE_FACTORY_TYPE, REFIID, IUnknown**> dwrite_create_factory_fn;
|
typedef HRESULT (*dwrite_create_factory_fn)(DWRITE_FACTORY_TYPE, REFIID, IUnknown **);
|
||||||
|
|
||||||
// Debugging functions
|
// Debugging functions
|
||||||
#ifdef DWRITE_DEBUGGING
|
#ifdef DWRITE_DEBUGGING
|
||||||
@ -96,13 +97,17 @@ HRESULT SaveBitmap(IWICBitmap* bitmap, GUID pixelFormat, const WCHAR *filename)
|
|||||||
ComPtr<IDWriteFactory> dwriteFactory;
|
ComPtr<IDWriteFactory> dwriteFactory;
|
||||||
ComPtr<IWICImagingFactory> wicFactory;
|
ComPtr<IWICImagingFactory> wicFactory;
|
||||||
|
|
||||||
d2d_create_factory_fn pfn_D2D1CreateFactory("D2D1CreateFactory", L"D2d1.dll");
|
osd::dynamic_module::ptr d2d1_dll = osd::dynamic_module::open({ "d2d1.dll" });
|
||||||
dwrite_create_factory_fn pfn_DWriteCreateFactory("DWriteCreateFactory", L"Dwrite.dll");
|
osd::dynamic_module::ptr dwrite_dll = osd::dynamic_module::open({ "dwrite.dll" });
|
||||||
HR_RETHR(pfn_D2D1CreateFactory.initialize());
|
|
||||||
HR_RETHR(pfn_DWriteCreateFactory.initialize());
|
d2d_create_factory_fn pfn_D2D1CreateFactory = d2d1_dll->bind<d2d_create_factory_fn>("D2D1CreateFactory");
|
||||||
|
dwrite_create_factory_fn pfn_DWriteCreateFactory = dwrite_dll->bind<dwrite_create_factory_fn>("DWriteCreateFactory");
|
||||||
|
|
||||||
|
if (!pfn_D2D1CreateFactory || !pfn_DWriteCreateFactory)
|
||||||
|
return ERROR_DLL_NOT_FOUND;
|
||||||
|
|
||||||
// Create a Direct2D factory
|
// Create a Direct2D factory
|
||||||
HR_RETHR(pfn_D2D1CreateFactory(
|
HR_RETHR((*pfn_D2D1CreateFactory)(
|
||||||
D2D1_FACTORY_TYPE_SINGLE_THREADED,
|
D2D1_FACTORY_TYPE_SINGLE_THREADED,
|
||||||
__uuidof(ID2D1Factory1),
|
__uuidof(ID2D1Factory1),
|
||||||
nullptr,
|
nullptr,
|
||||||
@ -112,7 +117,7 @@ HRESULT SaveBitmap(IWICBitmap* bitmap, GUID pixelFormat, const WCHAR *filename)
|
|||||||
CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED);
|
CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED);
|
||||||
|
|
||||||
// Create a DirectWrite factory.
|
// Create a DirectWrite factory.
|
||||||
HR_RETHR(pfn_DWriteCreateFactory(
|
HR_RETHR((*pfn_DWriteCreateFactory)(
|
||||||
DWRITE_FACTORY_TYPE_SHARED,
|
DWRITE_FACTORY_TYPE_SHARED,
|
||||||
__uuidof(IDWriteFactory),
|
__uuidof(IDWriteFactory),
|
||||||
reinterpret_cast<IUnknown **>(dwriteFactory.GetAddressOf())));
|
reinterpret_cast<IUnknown **>(dwriteFactory.GetAddressOf())));
|
||||||
@ -652,18 +657,18 @@ private:
|
|||||||
class font_dwrite : public osd_module, public font_module
|
class font_dwrite : public osd_module, public font_module
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
d2d_create_factory_fn m_pfnD2D1CreateFactory;
|
osd::dynamic_module::ptr m_d2d1_dll;
|
||||||
dwrite_create_factory_fn m_pfnDWriteCreateFactory;
|
osd::dynamic_module::ptr m_dwrite_dll;
|
||||||
ComPtr<ID2D1Factory> m_d2dfactory;
|
d2d_create_factory_fn m_pfnD2D1CreateFactory;
|
||||||
ComPtr<IDWriteFactory> m_dwriteFactory;
|
dwrite_create_factory_fn m_pfnDWriteCreateFactory;
|
||||||
ComPtr<IWICImagingFactory> m_wicFactory;
|
ComPtr<ID2D1Factory> m_d2dfactory;
|
||||||
|
ComPtr<IDWriteFactory> m_dwriteFactory;
|
||||||
|
ComPtr<IWICImagingFactory> m_wicFactory;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
font_dwrite() :
|
font_dwrite() :
|
||||||
osd_module(OSD_FONT_PROVIDER, "dwrite"),
|
osd_module(OSD_FONT_PROVIDER, "dwrite"),
|
||||||
font_module(),
|
font_module(),
|
||||||
m_pfnD2D1CreateFactory("D2D1CreateFactory", L"D2d1.dll"),
|
|
||||||
m_pfnDWriteCreateFactory("DWriteCreateFactory", L"Dwrite.dll"),
|
|
||||||
m_d2dfactory(nullptr),
|
m_d2dfactory(nullptr),
|
||||||
m_dwriteFactory(nullptr),
|
m_dwriteFactory(nullptr),
|
||||||
m_wicFactory(nullptr)
|
m_wicFactory(nullptr)
|
||||||
@ -672,12 +677,15 @@ public:
|
|||||||
|
|
||||||
virtual bool probe() override
|
virtual bool probe() override
|
||||||
{
|
{
|
||||||
|
m_d2d1_dll = osd::dynamic_module::open({ "d2d1.dll" });
|
||||||
|
m_dwrite_dll = osd::dynamic_module::open({ "dwrite.dll" });
|
||||||
|
|
||||||
|
m_pfnD2D1CreateFactory = m_d2d1_dll->bind<d2d_create_factory_fn>("D2D1CreateFactory");
|
||||||
|
m_pfnDWriteCreateFactory = m_dwrite_dll->bind<dwrite_create_factory_fn>("DWriteCreateFactory");
|
||||||
|
|
||||||
// This module is available if it can load the expected API Functions
|
// This module is available if it can load the expected API Functions
|
||||||
if (m_pfnD2D1CreateFactory.initialize() != 0
|
if (!m_pfnD2D1CreateFactory || !m_pfnDWriteCreateFactory)
|
||||||
|| m_pfnDWriteCreateFactory.initialize() != 0)
|
|
||||||
{
|
|
||||||
return false;
|
return false;
|
||||||
}
|
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -689,15 +697,14 @@ public:
|
|||||||
osd_printf_verbose("FontProvider: Initializing DirectWrite\n");
|
osd_printf_verbose("FontProvider: Initializing DirectWrite\n");
|
||||||
|
|
||||||
// Make sure we can initialize our api functions
|
// Make sure we can initialize our api functions
|
||||||
if (m_pfnD2D1CreateFactory.initialize()
|
if (!m_pfnD2D1CreateFactory || !m_pfnDWriteCreateFactory)
|
||||||
|| m_pfnDWriteCreateFactory.initialize())
|
|
||||||
{
|
{
|
||||||
osd_printf_error("ERROR: FontProvider: Failed to load DirectWrite functions.\n");
|
osd_printf_error("ERROR: FontProvider: Failed to load DirectWrite functions.\n");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
|
|
||||||
// Create a Direct2D factory.
|
// Create a Direct2D factory.
|
||||||
HR_RET1(m_pfnD2D1CreateFactory(
|
HR_RET1((*m_pfnD2D1CreateFactory)(
|
||||||
D2D1_FACTORY_TYPE_SINGLE_THREADED,
|
D2D1_FACTORY_TYPE_SINGLE_THREADED,
|
||||||
__uuidof(ID2D1Factory),
|
__uuidof(ID2D1Factory),
|
||||||
nullptr,
|
nullptr,
|
||||||
@ -707,7 +714,7 @@ public:
|
|||||||
CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED);
|
CoInitializeEx(nullptr, COINIT_APARTMENTTHREADED);
|
||||||
|
|
||||||
// Create a DirectWrite factory.
|
// Create a DirectWrite factory.
|
||||||
HR_RET1(m_pfnDWriteCreateFactory(
|
HR_RET1((*m_pfnDWriteCreateFactory)(
|
||||||
DWRITE_FACTORY_TYPE_SHARED,
|
DWRITE_FACTORY_TYPE_SHARED,
|
||||||
__uuidof(IDWriteFactory),
|
__uuidof(IDWriteFactory),
|
||||||
reinterpret_cast<IUnknown **>(m_dwriteFactory.GetAddressOf())));
|
reinterpret_cast<IUnknown **>(m_dwriteFactory.GetAddressOf())));
|
||||||
|
@ -136,8 +136,7 @@ void dinput_keyboard_device::reset()
|
|||||||
|
|
||||||
dinput_api_helper::dinput_api_helper(int version)
|
dinput_api_helper::dinput_api_helper(int version)
|
||||||
: m_dinput(nullptr),
|
: m_dinput(nullptr),
|
||||||
m_dinput_version(version),
|
m_dinput_version(version)
|
||||||
m_pfn_DirectInputCreate("DirectInputCreateW", L"dinput.dll")
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -163,18 +162,23 @@ int dinput_api_helper::initialize()
|
|||||||
else
|
else
|
||||||
#endif
|
#endif
|
||||||
{
|
{
|
||||||
result = m_pfn_DirectInputCreate.initialize();
|
m_dinput_dll = osd::dynamic_module::open({ "dinput.dll" });
|
||||||
if (result != DI_OK)
|
|
||||||
return result;
|
m_dinput_create_prt = m_dinput_dll->bind<dinput_create_fn>("DirectInputCreateW");
|
||||||
|
if (m_dinput_create_prt == nullptr)
|
||||||
|
{
|
||||||
|
osd_printf_verbose("Legacy DirectInput library dinput.dll is not available\n");
|
||||||
|
return ERROR_DLL_NOT_FOUND;
|
||||||
|
}
|
||||||
|
|
||||||
// first attempt to initialize DirectInput at v7
|
// first attempt to initialize DirectInput at v7
|
||||||
m_dinput_version = 0x0700;
|
m_dinput_version = 0x0700;
|
||||||
result = m_pfn_DirectInputCreate(GetModuleHandleUni(), m_dinput_version, m_dinput.GetAddressOf(), nullptr);
|
result = (*m_dinput_create_prt)(GetModuleHandleUni(), m_dinput_version, m_dinput.GetAddressOf(), nullptr);
|
||||||
if (result != DI_OK)
|
if (result != DI_OK)
|
||||||
{
|
{
|
||||||
// if that fails, try version 5
|
// if that fails, try version 5
|
||||||
m_dinput_version = 0x0500;
|
m_dinput_version = 0x0500;
|
||||||
result = m_pfn_DirectInputCreate(GetModuleHandleUni(), m_dinput_version, m_dinput.GetAddressOf(), nullptr);
|
result = (*m_dinput_create_prt)(GetModuleHandleUni(), m_dinput_version, m_dinput.GetAddressOf(), nullptr);
|
||||||
if (result != DI_OK)
|
if (result != DI_OK)
|
||||||
{
|
{
|
||||||
m_dinput_version = 0;
|
m_dinput_version = 0;
|
||||||
|
@ -2,7 +2,7 @@
|
|||||||
#define INPUT_DINPUT_H_
|
#define INPUT_DINPUT_H_
|
||||||
|
|
||||||
#include "input_common.h"
|
#include "input_common.h"
|
||||||
#include "winutil.h"
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// dinput_device - base directinput device
|
// dinput_device - base directinput device
|
||||||
@ -43,10 +43,11 @@ public:
|
|||||||
virtual BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) = 0;
|
virtual BOOL device_enum_callback(LPCDIDEVICEINSTANCE instance, LPVOID ref) = 0;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
// Typedef for dynamically loaded function
|
||||||
#if DIRECTINPUT_VERSION >= 0x0800
|
#if DIRECTINPUT_VERSION >= 0x0800
|
||||||
typedef lazy_loaded_function_p4<HRESULT, HMODULE, int, IDirectInput8 **, LPUNKNOWN> pfn_dinput_create;
|
typedef HRESULT WINAPI (*dinput_create_fn)(HINSTANCE, DWORD, LPDIRECTINPUT8 *, LPUNKNOWN);
|
||||||
#else
|
#else
|
||||||
typedef lazy_loaded_function_p4<HRESULT, HMODULE, int, IDirectInput **, LPUNKNOWN> pfn_dinput_create;
|
typedef HRESULT WINAPI (*dinput_create_fn)(HINSTANCE, DWORD, LPDIRECTINPUT *, LPUNKNOWN);
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
class dinput_api_helper
|
class dinput_api_helper
|
||||||
@ -58,7 +59,8 @@ private:
|
|||||||
Microsoft::WRL::ComPtr<IDirectInput> m_dinput;
|
Microsoft::WRL::ComPtr<IDirectInput> m_dinput;
|
||||||
#endif
|
#endif
|
||||||
int m_dinput_version;
|
int m_dinput_version;
|
||||||
pfn_dinput_create m_pfn_DirectInputCreate;
|
osd::dynamic_module::ptr m_dinput_dll;
|
||||||
|
dinput_create_fn m_dinput_create_prt;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
dinput_api_helper(int version);
|
dinput_api_helper(int version);
|
||||||
|
@ -26,7 +26,7 @@
|
|||||||
#include "strconv.h"
|
#include "strconv.h"
|
||||||
|
|
||||||
// MAMEOS headers
|
// MAMEOS headers
|
||||||
#include "winutil.h"
|
#include "modules/lib/osdlib.h"
|
||||||
#include "winmain.h"
|
#include "winmain.h"
|
||||||
#include "window.h"
|
#include "window.h"
|
||||||
|
|
||||||
@ -37,17 +37,11 @@
|
|||||||
// MACROS
|
// MACROS
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
#ifdef UNICODE
|
// Typedefs for dynamically loaded functions
|
||||||
#define UNICODE_SUFFIX "W"
|
typedef UINT WINAPI (*get_rawinput_device_list_ptr)(PRAWINPUTDEVICELIST, PUINT, UINT);
|
||||||
#else
|
typedef UINT WINAPI (*get_rawinput_data_ptr)( HRAWINPUT, UINT, LPVOID, PUINT, UINT);
|
||||||
#define UNICODE_SUFFIX "A"
|
typedef UINT WINAPI (*get_rawinput_device_info_ptr)(HANDLE, UINT, LPVOID, PUINT);
|
||||||
#endif
|
typedef BOOL WINAPI (*register_rawinput_devices_ptr)(PCRAWINPUTDEVICE, UINT, UINT);
|
||||||
|
|
||||||
// RawInput APIs
|
|
||||||
typedef lazy_loaded_function_p3<INT, PRAWINPUTDEVICELIST, PINT, UINT> get_rawinput_device_list_ptr;
|
|
||||||
typedef lazy_loaded_function_p5<INT, HRAWINPUT, UINT, LPVOID, PINT, UINT> get_rawinput_data_ptr;
|
|
||||||
typedef lazy_loaded_function_p4<INT, HANDLE, UINT, LPVOID, PINT> get_rawinput_device_info_ptr;
|
|
||||||
typedef lazy_loaded_function_p3<BOOL, PCRAWINPUTDEVICE, UINT, UINT> register_rawinput_devices_ptr;
|
|
||||||
|
|
||||||
class safe_regkey
|
class safe_regkey
|
||||||
{
|
{
|
||||||
@ -395,13 +389,6 @@ public:
|
|||||||
}
|
}
|
||||||
};
|
};
|
||||||
|
|
||||||
/*
|
|
||||||
register_rawinput_devices = (register_rawinput_devices_ptr)GetProcAddress(user32, "RegisterRawInputDevices");
|
|
||||||
get_rawinput_device_list = (get_rawinput_device_list_ptr)GetProcAddress(user32, "GetRawInputDeviceList");
|
|
||||||
get_rawinput_device_info = (get_rawinput_device_info_ptr)GetProcAddress(user32, "GetRawInputDeviceInfo" UNICODE_SUFFIX);
|
|
||||||
get_rawinput_data = (get_rawinput_data_ptr)GetProcAddress(user32, "GetRawInputData");
|
|
||||||
*/
|
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// rawinput_module - base class for rawinput modules
|
// rawinput_module - base class for rawinput modules
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -409,32 +396,33 @@ get_rawinput_data = (get_rawinput_data_ptr)GetProcAddress(user32, "GetRawInputDa
|
|||||||
class rawinput_module : public wininput_module
|
class rawinput_module : public wininput_module
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
// RawInput variables
|
osd::dynamic_module::ptr m_user32_dll;
|
||||||
get_rawinput_device_list_ptr get_rawinput_device_list;
|
get_rawinput_device_list_ptr get_rawinput_device_list;
|
||||||
get_rawinput_data_ptr get_rawinput_data;
|
get_rawinput_data_ptr get_rawinput_data;
|
||||||
get_rawinput_device_info_ptr get_rawinput_device_info;
|
get_rawinput_device_info_ptr get_rawinput_device_info;
|
||||||
register_rawinput_devices_ptr register_rawinput_devices;
|
register_rawinput_devices_ptr register_rawinput_devices;
|
||||||
std::mutex m_module_lock;
|
std::mutex m_module_lock;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
rawinput_module(const char *type, const char* name)
|
rawinput_module(const char *type, const char* name)
|
||||||
: wininput_module(type, name),
|
: wininput_module(type, name)
|
||||||
get_rawinput_device_list("GetRawInputDeviceList", L"user32.dll"),
|
|
||||||
get_rawinput_data("GetRawInputData", L"user32.dll"),
|
|
||||||
get_rawinput_device_info("GetRawInputDeviceInfoW", L"user32.dll"),
|
|
||||||
register_rawinput_devices("RegisterRawInputDevices", L"user32.dll")
|
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
|
|
||||||
bool probe() override
|
bool probe() override
|
||||||
{
|
{
|
||||||
int status = get_rawinput_device_list.initialize();
|
m_user32_dll = osd::dynamic_module::open({ "user32.dll" });
|
||||||
status |= get_rawinput_data.initialize();
|
|
||||||
status |= get_rawinput_device_info.initialize();
|
|
||||||
status |= register_rawinput_devices.initialize();
|
|
||||||
|
|
||||||
if (status != 0)
|
get_rawinput_device_list = m_user32_dll->bind<get_rawinput_device_list_ptr>("GetRawInputDeviceList");
|
||||||
|
get_rawinput_data = m_user32_dll->bind<get_rawinput_data_ptr>("GetRawInputData");
|
||||||
|
get_rawinput_device_info = m_user32_dll->bind<get_rawinput_device_info_ptr>("GetRawInputDeviceInfoW");
|
||||||
|
register_rawinput_devices = m_user32_dll->bind<register_rawinput_devices_ptr>("RegisterRawInputDevices");
|
||||||
|
|
||||||
|
if (!get_rawinput_device_list || !get_rawinput_data ||
|
||||||
|
!get_rawinput_device_info || !register_rawinput_devices )
|
||||||
|
{
|
||||||
return false;
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
@ -442,15 +430,15 @@ public:
|
|||||||
void input_init(running_machine &machine) override
|
void input_init(running_machine &machine) override
|
||||||
{
|
{
|
||||||
// get the number of devices, allocate a device list, and fetch it
|
// get the number of devices, allocate a device list, and fetch it
|
||||||
int device_count = 0;
|
UINT device_count = 0;
|
||||||
if (get_rawinput_device_list(nullptr, &device_count, sizeof(RAWINPUTDEVICELIST)) != 0)
|
if ((*get_rawinput_device_list)(nullptr, &device_count, sizeof(RAWINPUTDEVICELIST)) != 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
if (device_count == 0)
|
if (device_count == 0)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
auto rawinput_devices = std::make_unique<RAWINPUTDEVICELIST[]>(device_count);
|
auto rawinput_devices = std::make_unique<RAWINPUTDEVICELIST[]>(device_count);
|
||||||
if (get_rawinput_device_list(rawinput_devices.get(), &device_count, sizeof(RAWINPUTDEVICELIST)) == -1)
|
if ((*get_rawinput_device_list)(rawinput_devices.get(), &device_count, sizeof(RAWINPUTDEVICELIST)) == -1)
|
||||||
return;
|
return;
|
||||||
|
|
||||||
// iterate backwards through devices; new devices are added at the head
|
// iterate backwards through devices; new devices are added at the head
|
||||||
@ -478,7 +466,7 @@ public:
|
|||||||
registration.hwndTarget = osd_common_t::s_window_list.front()->platform_window<HWND>();
|
registration.hwndTarget = osd_common_t::s_window_list.front()->platform_window<HWND>();
|
||||||
|
|
||||||
// register the device
|
// register the device
|
||||||
register_rawinput_devices(®istration, 1, sizeof(registration));
|
(*register_rawinput_devices)(®istration, 1, sizeof(registration));
|
||||||
}
|
}
|
||||||
|
|
||||||
protected:
|
protected:
|
||||||
@ -488,13 +476,11 @@ protected:
|
|||||||
|
|
||||||
int init_internal() override
|
int init_internal() override
|
||||||
{
|
{
|
||||||
// look up the entry points
|
if (!get_rawinput_device_list || !get_rawinput_data ||
|
||||||
int status = get_rawinput_device_list.initialize();
|
!get_rawinput_device_info || !register_rawinput_devices )
|
||||||
status |= get_rawinput_data.initialize();
|
{
|
||||||
status |= get_rawinput_device_info.initialize();
|
|
||||||
status |= register_rawinput_devices.initialize();
|
|
||||||
if (status != 0)
|
|
||||||
return 1;
|
return 1;
|
||||||
|
}
|
||||||
|
|
||||||
osd_printf_verbose("RawInput: APIs detected\n");
|
osd_printf_verbose("RawInput: APIs detected\n");
|
||||||
return 0;
|
return 0;
|
||||||
@ -504,13 +490,13 @@ protected:
|
|||||||
TDevice* create_rawinput_device(running_machine &machine, PRAWINPUTDEVICELIST rawinputdevice)
|
TDevice* create_rawinput_device(running_machine &machine, PRAWINPUTDEVICELIST rawinputdevice)
|
||||||
{
|
{
|
||||||
TDevice* devinfo;
|
TDevice* devinfo;
|
||||||
INT name_length = 0;
|
UINT name_length = 0;
|
||||||
// determine the length of the device name, allocate it, and fetch it if not nameless
|
// determine the length of the device name, allocate it, and fetch it if not nameless
|
||||||
if (get_rawinput_device_info(rawinputdevice->hDevice, RIDI_DEVICENAME, nullptr, &name_length) != 0)
|
if ((*get_rawinput_device_info)(rawinputdevice->hDevice, RIDI_DEVICENAME, nullptr, &name_length) != 0)
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
std::unique_ptr<TCHAR[]> tname = std::make_unique<TCHAR[]>(name_length + 1);
|
std::unique_ptr<TCHAR[]> tname = std::make_unique<TCHAR[]>(name_length + 1);
|
||||||
if (name_length > 1 && get_rawinput_device_info(rawinputdevice->hDevice, RIDI_DEVICENAME, tname.get(), &name_length) == -1)
|
if (name_length > 1 && (*get_rawinput_device_info)(rawinputdevice->hDevice, RIDI_DEVICENAME, tname.get(), &name_length) == -1)
|
||||||
return nullptr;
|
return nullptr;
|
||||||
|
|
||||||
// if this is an RDP name, skip it
|
// if this is an RDP name, skip it
|
||||||
@ -544,14 +530,14 @@ protected:
|
|||||||
std::unique_ptr<BYTE[]> larger_buffer;
|
std::unique_ptr<BYTE[]> larger_buffer;
|
||||||
LPBYTE data = small_buffer;
|
LPBYTE data = small_buffer;
|
||||||
BOOL result;
|
BOOL result;
|
||||||
int size;
|
UINT size;
|
||||||
|
|
||||||
// ignore if not enabled
|
// ignore if not enabled
|
||||||
if (!input_enabled())
|
if (!input_enabled())
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
// determine the size of databuffer we need
|
// determine the size of databuffer we need
|
||||||
if (get_rawinput_data(rawinputdevice, RID_INPUT, nullptr, &size, sizeof(RAWINPUTHEADER)) != 0)
|
if ((*get_rawinput_data)(rawinputdevice, RID_INPUT, nullptr, &size, sizeof(RAWINPUTHEADER)) != 0)
|
||||||
return FALSE;
|
return FALSE;
|
||||||
|
|
||||||
// if necessary, allocate a temporary buffer and fetch the data
|
// if necessary, allocate a temporary buffer and fetch the data
|
||||||
@ -564,7 +550,7 @@ protected:
|
|||||||
}
|
}
|
||||||
|
|
||||||
// fetch the data and process the appropriate message types
|
// fetch the data and process the appropriate message types
|
||||||
result = get_rawinput_data(static_cast<HRAWINPUT>(rawinputdevice), RID_INPUT, data, &size, sizeof(RAWINPUTHEADER));
|
result = (*get_rawinput_data)(static_cast<HRAWINPUT>(rawinputdevice), RID_INPUT, data, &size, sizeof(RAWINPUTHEADER));
|
||||||
if (result)
|
if (result)
|
||||||
{
|
{
|
||||||
std::lock_guard<std::mutex> scope_lock(m_module_lock);
|
std::lock_guard<std::mutex> scope_lock(m_module_lock);
|
||||||
|
@ -218,7 +218,7 @@ protected:
|
|||||||
{
|
{
|
||||||
XINPUT_STATE state = { 0 };
|
XINPUT_STATE state = { 0 };
|
||||||
|
|
||||||
if (m_xinput_helper->XInputGetState(i, &state) == ERROR_SUCCESS)
|
if (m_xinput_helper->xinput_get_state(i, &state) == ERROR_SUCCESS)
|
||||||
{
|
{
|
||||||
// allocate and link in a new device
|
// allocate and link in a new device
|
||||||
devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
|
devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
|
||||||
|
@ -32,50 +32,28 @@
|
|||||||
#include "input_windows.h"
|
#include "input_windows.h"
|
||||||
#include "input_xinput.h"
|
#include "input_xinput.h"
|
||||||
|
|
||||||
|
|
||||||
xinput_api_helper::xinput_api_helper()
|
|
||||||
#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
||||||
: XInputGetState("XInputGetState", xinput_dll_names, ARRAY_LENGTH(xinput_dll_names))
|
#define XINPUT_LIBRARIES { "xinput1_4.dll", "xinput9_1_0.dll" }
|
||||||
, XInputGetCapabilities("XInputGetCapabilities", xinput_dll_names, ARRAY_LENGTH(xinput_dll_names))
|
#else
|
||||||
|
#define XINPUT_LIBRARIES { "xinput1_4.dll" }
|
||||||
#endif
|
#endif
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
int xinput_api_helper::initialize()
|
int xinput_api_helper::initialize()
|
||||||
{
|
{
|
||||||
#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
m_xinput_dll = osd::dynamic_module::open(XINPUT_LIBRARIES);
|
||||||
int status;
|
|
||||||
status = XInputGetState.initialize();
|
|
||||||
if (status != 0)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Failed to initialize function pointer for %s. Error: %d\n", XInputGetState.name(), status);
|
|
||||||
return -1;
|
|
||||||
}
|
|
||||||
|
|
||||||
status = XInputGetCapabilities.initialize();
|
XInputGetState = m_xinput_dll->bind<xinput_get_state_fn>("XInputGetState");
|
||||||
if (status != 0)
|
XInputGetCapabilities = m_xinput_dll->bind<xinput_get_caps_fn>("XInputGetCapabilities");
|
||||||
|
|
||||||
|
if (!XInputGetState || !XInputGetCapabilities)
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Failed to initialize function pointer for %s. Error: %d\n", XInputGetCapabilities.name(), status);
|
osd_printf_verbose("Could not find XInput. Please try to reinstall DirectX runtime package.\n");
|
||||||
return -1;
|
return -1;
|
||||||
}
|
}
|
||||||
#endif
|
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
|
|
||||||
#if !WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
|
||||||
// Pass-through functions for Universal Windows
|
|
||||||
inline DWORD xinput_api_helper::XInputGetState(DWORD dwUserindex, XINPUT_STATE *pState)
|
|
||||||
{
|
|
||||||
return ::XInputGetState(dwUserindex, pState);
|
|
||||||
}
|
|
||||||
|
|
||||||
inline DWORD xinput_api_helper::XInputGetCapabilities(DWORD dwUserindex, DWORD dwFlags, XINPUT_CAPABILITIES* pCapabilities)
|
|
||||||
{
|
|
||||||
return ::XInputGetCapabilities(dwUserindex, dwFlags, pCapabilities);
|
|
||||||
}
|
|
||||||
#endif
|
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// create_xinput_device
|
// create_xinput_device
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -85,7 +63,7 @@ xinput_joystick_device * xinput_api_helper::create_xinput_device(running_machine
|
|||||||
xinput_joystick_device *devinfo;
|
xinput_joystick_device *devinfo;
|
||||||
|
|
||||||
XINPUT_CAPABILITIES caps = { 0 };
|
XINPUT_CAPABILITIES caps = { 0 };
|
||||||
if (FAILED(XInputGetCapabilities(index, 0, &caps)))
|
if (FAILED(xinput_get_capabilities(index, 0, &caps)))
|
||||||
{
|
{
|
||||||
// If we can't get the capabilities skip this device
|
// If we can't get the capabilities skip this device
|
||||||
return nullptr;
|
return nullptr;
|
||||||
@ -125,7 +103,7 @@ void xinput_joystick_device::poll()
|
|||||||
return;
|
return;
|
||||||
|
|
||||||
// poll the device first
|
// poll the device first
|
||||||
HRESULT result = m_xinput_helper->XInputGetState(xinput_state.player_index, &xinput_state.xstate);
|
HRESULT result = m_xinput_helper->xinput_get_state(xinput_state.player_index, &xinput_state.xstate);
|
||||||
|
|
||||||
// If we can't poll the device, skip
|
// If we can't poll the device, skip
|
||||||
if (FAILED(result))
|
if (FAILED(result))
|
||||||
@ -262,7 +240,7 @@ protected:
|
|||||||
{
|
{
|
||||||
XINPUT_STATE state = {0};
|
XINPUT_STATE state = {0};
|
||||||
|
|
||||||
if (m_xinput_helper->XInputGetState(i, &state) == ERROR_SUCCESS)
|
if (m_xinput_helper->xinput_get_state(i, &state) == ERROR_SUCCESS)
|
||||||
{
|
{
|
||||||
// allocate and link in a new device
|
// allocate and link in a new device
|
||||||
devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
|
devinfo = m_xinput_helper->create_xinput_device(machine, i, *this);
|
||||||
|
@ -3,6 +3,8 @@
|
|||||||
|
|
||||||
#include <mutex>
|
#include <mutex>
|
||||||
|
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
#define XINPUT_MAX_POV 4
|
#define XINPUT_MAX_POV 4
|
||||||
#define XINPUT_MAX_BUTTONS 10
|
#define XINPUT_MAX_BUTTONS 10
|
||||||
#define XINPUT_MAX_AXIS 4
|
#define XINPUT_MAX_AXIS 4
|
||||||
@ -88,34 +90,30 @@ struct xinput_api_state
|
|||||||
XINPUT_CAPABILITIES caps;
|
XINPUT_CAPABILITIES caps;
|
||||||
};
|
};
|
||||||
|
|
||||||
#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
// Typedefs for dynamically loaded functions
|
||||||
// Typedef for pointers to XInput Functions
|
typedef DWORD (*xinput_get_state_fn)(DWORD, XINPUT_STATE *);
|
||||||
typedef lazy_loaded_function_p2<DWORD, DWORD, XINPUT_STATE*> xinput_get_state_fn;
|
typedef DWORD (*xinput_get_caps_fn)(DWORD, DWORD, XINPUT_CAPABILITIES *);
|
||||||
typedef lazy_loaded_function_p3<DWORD, DWORD, DWORD, XINPUT_CAPABILITIES*> xinput_get_caps_fn;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
class xinput_api_helper : public std::enable_shared_from_this<xinput_api_helper>
|
class xinput_api_helper : public std::enable_shared_from_this<xinput_api_helper>
|
||||||
{
|
{
|
||||||
#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
|
||||||
private:
|
|
||||||
const wchar_t* xinput_dll_names[2] = { L"xinput1_4.dll", L"xinput9_1_0.dll" };
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
xinput_get_state_fn XInputGetState;
|
|
||||||
xinput_get_caps_fn XInputGetCapabilities;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
public:
|
|
||||||
xinput_api_helper();
|
|
||||||
|
|
||||||
int initialize();
|
int initialize();
|
||||||
xinput_joystick_device * create_xinput_device(running_machine &machine, UINT index, wininput_module &module);
|
xinput_joystick_device * create_xinput_device(running_machine &machine, UINT index, wininput_module &module);
|
||||||
|
|
||||||
#if !WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
inline DWORD xinput_get_state(DWORD dwUserindex, XINPUT_STATE *pState)
|
||||||
// Pass-through functions for Universal Windows
|
{
|
||||||
inline DWORD XInputGetState(DWORD dwUserindex, XINPUT_STATE *pState);
|
return (*XInputGetState)(dwUserindex, pState);
|
||||||
inline DWORD XInputGetCapabilities(DWORD dwUserindex, DWORD dwFlags, XINPUT_CAPABILITIES* pCapabilities);
|
}
|
||||||
#endif
|
|
||||||
|
inline DWORD xinput_get_capabilities(DWORD dwUserindex, DWORD dwFlags, XINPUT_CAPABILITIES* pCapabilities)
|
||||||
|
{
|
||||||
|
return (*XInputGetCapabilities)(dwUserindex, dwFlags, pCapabilities);
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
osd::dynamic_module::ptr m_xinput_dll;
|
||||||
|
xinput_get_state_fn XInputGetState;
|
||||||
|
xinput_get_caps_fn XInputGetCapabilities;
|
||||||
};
|
};
|
||||||
|
|
||||||
class xinput_joystick_device : public device_info
|
class xinput_joystick_device : public device_info
|
||||||
|
@ -19,6 +19,10 @@
|
|||||||
#ifndef __OSDLIB__
|
#ifndef __OSDLIB__
|
||||||
#define __OSDLIB__
|
#define __OSDLIB__
|
||||||
|
|
||||||
|
#include <string>
|
||||||
|
#include <type_traits>
|
||||||
|
#include <vector>
|
||||||
|
|
||||||
/*-----------------------------------------------------------------------------
|
/*-----------------------------------------------------------------------------
|
||||||
osd_process_kill: kill the current process
|
osd_process_kill: kill the current process
|
||||||
|
|
||||||
@ -30,8 +34,10 @@
|
|||||||
|
|
||||||
None.
|
None.
|
||||||
-----------------------------------------------------------------------------*/
|
-----------------------------------------------------------------------------*/
|
||||||
|
|
||||||
void osd_process_kill(void);
|
void osd_process_kill(void);
|
||||||
|
|
||||||
|
|
||||||
/*-----------------------------------------------------------------------------
|
/*-----------------------------------------------------------------------------
|
||||||
osd_setenv: set environment variable
|
osd_setenv: set environment variable
|
||||||
|
|
||||||
@ -48,14 +54,52 @@ void osd_process_kill(void);
|
|||||||
|
|
||||||
int osd_setenv(const char *name, const char *value, int overwrite);
|
int osd_setenv(const char *name, const char *value, int overwrite);
|
||||||
|
|
||||||
|
|
||||||
/*-----------------------------------------------------------------------------
|
/*-----------------------------------------------------------------------------
|
||||||
osd_get_clipboard_text: retrieves text from the clipboard
|
osd_get_clipboard_text: retrieves text from the clipboard
|
||||||
|
|
||||||
Return value:
|
Return value:
|
||||||
|
|
||||||
the returned string needs to be osd_free()-ed!
|
the returned string needs to be osd_free()-ed!
|
||||||
|
|
||||||
-----------------------------------------------------------------------------*/
|
-----------------------------------------------------------------------------*/
|
||||||
|
|
||||||
char *osd_get_clipboard_text(void);
|
char *osd_get_clipboard_text(void);
|
||||||
|
|
||||||
|
|
||||||
|
/*-----------------------------------------------------------------------------
|
||||||
|
dynamic_module: load functions from optional shared libraries
|
||||||
|
|
||||||
|
Notes:
|
||||||
|
|
||||||
|
- Supports Mac OS X, Unix and Windows (both desktop and Windows
|
||||||
|
Store universal applications)
|
||||||
|
- A symbol can be searched in a list of libraries (e.g. more
|
||||||
|
revisions of a same library)
|
||||||
|
-----------------------------------------------------------------------------*/
|
||||||
|
|
||||||
|
namespace osd {
|
||||||
|
|
||||||
|
class dynamic_module
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
typedef std::unique_ptr<dynamic_module> ptr;
|
||||||
|
|
||||||
|
static ptr open(std::vector<std::string> &&libraries);
|
||||||
|
|
||||||
|
virtual ~dynamic_module() { };
|
||||||
|
|
||||||
|
template <typename T>
|
||||||
|
typename std::enable_if<std::is_pointer<T>::value, T>::type bind(char const *symbol)
|
||||||
|
{
|
||||||
|
return reinterpret_cast<T>(get_symbol_address(symbol));
|
||||||
|
}
|
||||||
|
|
||||||
|
protected:
|
||||||
|
typedef void (*generic_fptr_t)();
|
||||||
|
|
||||||
|
virtual generic_fptr_t get_symbol_address(char const *symbol) = 0;
|
||||||
|
};
|
||||||
|
|
||||||
|
} // namespace osd
|
||||||
|
|
||||||
#endif /* __OSDLIB__ */
|
#endif /* __OSDLIB__ */
|
||||||
|
@ -13,6 +13,12 @@
|
|||||||
#include <sys/mman.h>
|
#include <sys/mman.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <signal.h>
|
#include <signal.h>
|
||||||
|
#include <dlfcn.h>
|
||||||
|
|
||||||
|
#include <codecvt>
|
||||||
|
#include <iomanip>
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
|
|
||||||
#include <mach/mach.h>
|
#include <mach/mach.h>
|
||||||
#include <mach/mach_time.h>
|
#include <mach/mach_time.h>
|
||||||
@ -215,3 +221,71 @@ char *osd_get_clipboard_text(void)
|
|||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//============================================================
|
||||||
|
// dynamic_module_posix_impl
|
||||||
|
//============================================================
|
||||||
|
|
||||||
|
namespace osd {
|
||||||
|
|
||||||
|
class dynamic_module_posix_impl : public dynamic_module
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
dynamic_module_posix_impl(std::vector<std::string> &libraries)
|
||||||
|
: m_module(nullptr)
|
||||||
|
{
|
||||||
|
m_libraries = libraries;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual ~dynamic_module_posix_impl() override
|
||||||
|
{
|
||||||
|
if (m_module != nullptr)
|
||||||
|
dlclose(m_module);
|
||||||
|
};
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual generic_fptr_t get_symbol_address(char const *symbol) override
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* given a list of libraries, if a first symbol is successfully loaded from
|
||||||
|
* one of them, all additional symbols will be loaded from the same library
|
||||||
|
*/
|
||||||
|
if (m_module)
|
||||||
|
{
|
||||||
|
return reinterpret_cast<generic_fptr_t>(dlsym(m_module, symbol));
|
||||||
|
}
|
||||||
|
|
||||||
|
for (auto const &library : m_libraries)
|
||||||
|
{
|
||||||
|
void *module = dlopen(library.c_str(), RTLD_LAZY);
|
||||||
|
|
||||||
|
if (module != nullptr)
|
||||||
|
{
|
||||||
|
generic_fptr_t function = reinterpret_cast<generic_fptr_t>(dlsym(module, symbol));
|
||||||
|
|
||||||
|
if (function != nullptr)
|
||||||
|
{
|
||||||
|
m_module = module;
|
||||||
|
return function;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dlclose(module);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::vector<std::string> m_libraries;
|
||||||
|
void * m_module;
|
||||||
|
};
|
||||||
|
|
||||||
|
dynamic_module::ptr dynamic_module::open(std::vector<std::string> &&names)
|
||||||
|
{
|
||||||
|
return std::make_unique<dynamic_module_posix_impl>(names);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace osd
|
||||||
|
@ -13,12 +13,19 @@
|
|||||||
#include <sys/mman.h>
|
#include <sys/mman.h>
|
||||||
#include <sys/types.h>
|
#include <sys/types.h>
|
||||||
#include <signal.h>
|
#include <signal.h>
|
||||||
|
#include <dlfcn.h>
|
||||||
|
|
||||||
|
#include <codecvt>
|
||||||
|
#include <iomanip>
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
|
|
||||||
// MAME headers
|
// MAME headers
|
||||||
#include "osdcore.h"
|
#include "osdcore.h"
|
||||||
#include "osdlib.h"
|
#include "osdlib.h"
|
||||||
|
|
||||||
#include <SDL2/SDL.h>
|
#include <SDL2/SDL.h>
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// osd_getenv
|
// osd_getenv
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -159,3 +166,71 @@ char *osd_get_clipboard_text(void)
|
|||||||
}
|
}
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
//============================================================
|
||||||
|
// dynamic_module_posix_impl
|
||||||
|
//============================================================
|
||||||
|
|
||||||
|
namespace osd {
|
||||||
|
|
||||||
|
class dynamic_module_posix_impl : public dynamic_module
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
dynamic_module_posix_impl(std::vector<std::string> &libraries)
|
||||||
|
: m_module(nullptr)
|
||||||
|
{
|
||||||
|
m_libraries = libraries;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual ~dynamic_module_posix_impl() override
|
||||||
|
{
|
||||||
|
if (m_module != nullptr)
|
||||||
|
dlclose(m_module);
|
||||||
|
};
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual generic_fptr_t get_symbol_address(char const *symbol) override
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* given a list of libraries, if a first symbol is successfully loaded from
|
||||||
|
* one of them, all additional symbols will be loaded from the same library
|
||||||
|
*/
|
||||||
|
if (m_module)
|
||||||
|
{
|
||||||
|
return reinterpret_cast<generic_fptr_t>(dlsym(m_module, symbol));
|
||||||
|
}
|
||||||
|
|
||||||
|
for (auto const &library : m_libraries)
|
||||||
|
{
|
||||||
|
void *module = dlopen(library.c_str(), RTLD_LAZY);
|
||||||
|
|
||||||
|
if (module != nullptr)
|
||||||
|
{
|
||||||
|
generic_fptr_t function = reinterpret_cast<generic_fptr_t>(dlsym(module, symbol));
|
||||||
|
|
||||||
|
if (function != nullptr)
|
||||||
|
{
|
||||||
|
m_module = module;
|
||||||
|
return function;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
dlclose(module);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::vector<std::string> m_libraries;
|
||||||
|
void * m_module;
|
||||||
|
};
|
||||||
|
|
||||||
|
dynamic_module::ptr dynamic_module::open(std::vector<std::string> &&names)
|
||||||
|
{
|
||||||
|
return std::make_unique<dynamic_module_posix_impl>(names);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace osd
|
||||||
|
@ -17,6 +17,8 @@
|
|||||||
#include <unistd.h>
|
#include <unistd.h>
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
|
#include <memory>
|
||||||
|
|
||||||
// MAME headers
|
// MAME headers
|
||||||
#include "osdlib.h"
|
#include "osdlib.h"
|
||||||
#include "osdcomm.h"
|
#include "osdcomm.h"
|
||||||
@ -314,3 +316,85 @@ char *osd_get_clipboard_text(void)
|
|||||||
|
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
//============================================================
|
||||||
|
// osd_dynamic_bind
|
||||||
|
//============================================================
|
||||||
|
|
||||||
|
#if WINAPI_FAMILY_PARTITION(WINAPI_PARTITION_DESKTOP)
|
||||||
|
// for classic desktop applications
|
||||||
|
#define load_library(filename) LoadLibrary(filename)
|
||||||
|
#else
|
||||||
|
// for Windows Store universal applications
|
||||||
|
#define load_library(filename) LoadPackagedLibrary(filename, 0)
|
||||||
|
#endif
|
||||||
|
|
||||||
|
namespace osd {
|
||||||
|
|
||||||
|
class dynamic_module_win32_impl : public dynamic_module
|
||||||
|
{
|
||||||
|
public:
|
||||||
|
dynamic_module_win32_impl(std::vector<std::string> &libraries)
|
||||||
|
: m_module(nullptr)
|
||||||
|
{
|
||||||
|
m_libraries = libraries;
|
||||||
|
}
|
||||||
|
|
||||||
|
virtual ~dynamic_module_win32_impl() override
|
||||||
|
{
|
||||||
|
if (m_module != nullptr)
|
||||||
|
FreeLibrary(m_module);
|
||||||
|
};
|
||||||
|
|
||||||
|
protected:
|
||||||
|
virtual generic_fptr_t get_symbol_address(char const *symbol) override
|
||||||
|
{
|
||||||
|
/*
|
||||||
|
* given a list of libraries, if a first symbol is successfully loaded from
|
||||||
|
* one of them, all additional symbols will be loaded from the same library
|
||||||
|
*/
|
||||||
|
if (m_module)
|
||||||
|
{
|
||||||
|
return reinterpret_cast<generic_fptr_t>(GetProcAddress(m_module, symbol));
|
||||||
|
}
|
||||||
|
|
||||||
|
for (auto const &library : m_libraries)
|
||||||
|
{
|
||||||
|
TCHAR *tempstr = tstring_from_utf8(library.c_str());
|
||||||
|
if (!tempstr)
|
||||||
|
return nullptr;
|
||||||
|
|
||||||
|
HMODULE module = load_library(tempstr);
|
||||||
|
|
||||||
|
osd_free(tempstr);
|
||||||
|
|
||||||
|
if (module != nullptr)
|
||||||
|
{
|
||||||
|
generic_fptr_t function = reinterpret_cast<generic_fptr_t>(GetProcAddress(module, symbol));
|
||||||
|
|
||||||
|
if (function != nullptr)
|
||||||
|
{
|
||||||
|
m_module = module;
|
||||||
|
return function;
|
||||||
|
}
|
||||||
|
else
|
||||||
|
{
|
||||||
|
FreeLibrary(module);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
|
return nullptr;
|
||||||
|
}
|
||||||
|
|
||||||
|
private:
|
||||||
|
std::vector<std::string> m_libraries;
|
||||||
|
HMODULE m_module;
|
||||||
|
};
|
||||||
|
|
||||||
|
dynamic_module::ptr dynamic_module::open(std::vector<std::string> &&names)
|
||||||
|
{
|
||||||
|
return std::make_unique<dynamic_module_win32_impl>(names);
|
||||||
|
}
|
||||||
|
|
||||||
|
} // namespace osd
|
||||||
|
@ -1,61 +1,47 @@
|
|||||||
// license:BSD-3-Clause
|
// license:BSD-3-Clause
|
||||||
// copyright-holders:Carl
|
// copyright-holders:Carl
|
||||||
|
|
||||||
#if defined(OSD_NET_USE_PCAP)
|
#if defined(OSD_NET_USE_PCAP)
|
||||||
|
|
||||||
#if defined(SDLMAME_WIN32) || defined(OSD_WINDOWS)
|
|
||||||
#ifdef UNICODE
|
|
||||||
#define LIB_NAME L"wpcap.dll"
|
|
||||||
#define LoadDynamicLibrary LoadLibraryW
|
|
||||||
#else
|
|
||||||
#define LIB_NAME "wpcap.dll"
|
|
||||||
#define LoadDynamicLibrary LoadLibraryA
|
|
||||||
#endif
|
|
||||||
#define WIN32_LEAN_AND_MEAN
|
|
||||||
#include <windows.h>
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#include <pcap.h>
|
|
||||||
|
|
||||||
#include "emu.h"
|
#include "emu.h"
|
||||||
#include "osdnet.h"
|
#include "osdnet.h"
|
||||||
#include "netdev_module.h"
|
#include "netdev_module.h"
|
||||||
#include "modules/osdmodule.h"
|
#include "modules/osdmodule.h"
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
#if defined(SDLMAME_WIN32) || defined(OSD_WINDOWS)
|
#if defined(SDLMAME_WIN32) || defined(OSD_WINDOWS)
|
||||||
|
#define WIN32_LEAN_AND_MEAN
|
||||||
|
#include <windows.h>
|
||||||
|
#undef interface
|
||||||
|
#define LIB_NAME "wpcap.dll"
|
||||||
|
|
||||||
#define LIB_ERROR_STR "Unable to load winpcap: %lx\n"
|
#elif defined(SDLMAME_MACOSX)
|
||||||
typedef DWORD except_type;
|
|
||||||
|
|
||||||
#else
|
|
||||||
|
|
||||||
#include <dlfcn.h>
|
|
||||||
#ifdef SDLMAME_MACOSX
|
|
||||||
#include <pthread.h>
|
#include <pthread.h>
|
||||||
#include <libkern/OSAtomic.h>
|
#include <libkern/OSAtomic.h>
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef SDLMAME_MACOSX
|
|
||||||
#define LIB_NAME "libpcap.dylib"
|
#define LIB_NAME "libpcap.dylib"
|
||||||
|
|
||||||
#else
|
#else
|
||||||
#define LIB_NAME "libpcap.so"
|
#define LIB_NAME "libpcap.so"
|
||||||
#endif
|
#endif
|
||||||
#define LIB_ERROR_STR "Unable to load pcap: %s\n"
|
|
||||||
|
|
||||||
typedef void *HMODULE;
|
#include <pcap.h>
|
||||||
typedef const char *except_type;
|
|
||||||
#define FreeLibrary(x) dlclose(x)
|
|
||||||
#define GetLastError() dlerror()
|
|
||||||
#define GetProcAddress(x, y) dlsym(x, y)
|
|
||||||
#define LoadDynamicLibrary(x) dlopen(x, RTLD_LAZY)
|
|
||||||
|
|
||||||
#endif
|
// Typedefs for dynamically loaded functions
|
||||||
|
typedef int (*pcap_findalldevs_fn)(pcap_if_t **, char *);
|
||||||
|
typedef pcap_t *(*pcap_open_live_fn)(const char *, int, int, int, char *);
|
||||||
|
typedef int (*pcap_next_ex_fn)(pcap_t *, struct pcap_pkthdr **, const u_char **);
|
||||||
|
typedef int (*pcap_compile_fn)(pcap_t *, struct bpf_program *, const char *, int, bpf_u_int32);
|
||||||
|
typedef void (*pcap_close_fn)(pcap_t *);
|
||||||
|
typedef int (*pcap_setfilter_fn)(pcap_t *, struct bpf_program *);
|
||||||
|
typedef int (*pcap_sendpacket_fn)(pcap_t *, const u_char *, int);
|
||||||
|
typedef int (*pcap_set_datalink_fn)(pcap_t *, int);
|
||||||
|
typedef int (*pcap_dispatch_fn)(pcap_t *, int, pcap_handler, u_char *);
|
||||||
|
|
||||||
class pcap_module : public osd_module, public netdev_module
|
class pcap_module : public osd_module, public netdev_module
|
||||||
{
|
{
|
||||||
public:
|
public:
|
||||||
|
|
||||||
pcap_module()
|
pcap_module()
|
||||||
: osd_module(OSD_NETDEV_PROVIDER, "pcap"), netdev_module(), handle(nullptr)
|
: osd_module(OSD_NETDEV_PROVIDER, "pcap"), netdev_module()
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
virtual ~pcap_module() { }
|
virtual ~pcap_module() { }
|
||||||
@ -63,32 +49,46 @@ public:
|
|||||||
virtual int init(const osd_options &options) override;
|
virtual int init(const osd_options &options) override;
|
||||||
virtual void exit() override;
|
virtual void exit() override;
|
||||||
|
|
||||||
virtual bool probe() override;
|
virtual bool probe() override
|
||||||
|
{
|
||||||
|
pcap_dll = osd::dynamic_module::open({ LIB_NAME });
|
||||||
|
|
||||||
HMODULE handle;
|
pcap_findalldevs_dl = pcap_dll->bind<pcap_findalldevs_fn>("pcap_findalldevs");
|
||||||
|
pcap_open_live_dl = pcap_dll->bind<pcap_open_live_fn>("pcap_open_live");
|
||||||
|
pcap_next_ex_dl = pcap_dll->bind<pcap_next_ex_fn>("pcap_next_ex");
|
||||||
|
pcap_compile_dl = pcap_dll->bind<pcap_compile_fn>("pcap_compile");
|
||||||
|
pcap_close_dl = pcap_dll->bind<pcap_close_fn>("pcap_close");
|
||||||
|
pcap_setfilter_dl = pcap_dll->bind<pcap_setfilter_fn>("pcap_setfilter");
|
||||||
|
pcap_sendpacket_dl = pcap_dll->bind<pcap_sendpacket_fn>("pcap_sendpacket");
|
||||||
|
pcap_set_datalink_dl = pcap_dll->bind<pcap_set_datalink_fn>("pcap_set_datalink");
|
||||||
|
pcap_dispatch_dl = pcap_dll->bind<pcap_dispatch_fn>("pcap_dispatch");
|
||||||
|
|
||||||
|
if (!pcap_findalldevs_dl || !pcap_open_live_dl || !pcap_next_ex_dl ||
|
||||||
|
!pcap_compile_dl || !pcap_close_dl || !pcap_setfilter_dl ||
|
||||||
|
!pcap_sendpacket_dl || !pcap_set_datalink_dl || !pcap_dispatch_dl)
|
||||||
|
{
|
||||||
|
osd_printf_error("Unable to load the PCAP library\n");
|
||||||
|
return false;
|
||||||
|
}
|
||||||
|
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
osd::dynamic_module::ptr pcap_dll;
|
||||||
|
|
||||||
|
pcap_findalldevs_fn pcap_findalldevs_dl;
|
||||||
|
pcap_open_live_fn pcap_open_live_dl;
|
||||||
|
pcap_next_ex_fn pcap_next_ex_dl;
|
||||||
|
pcap_compile_fn pcap_compile_dl;
|
||||||
|
pcap_close_fn pcap_close_dl;
|
||||||
|
pcap_setfilter_fn pcap_setfilter_dl;
|
||||||
|
pcap_sendpacket_fn pcap_sendpacket_dl;
|
||||||
|
pcap_set_datalink_fn pcap_set_datalink_dl;
|
||||||
|
pcap_dispatch_fn pcap_dispatch_dl;
|
||||||
};
|
};
|
||||||
|
|
||||||
static int (*pcap_compile_dl)(pcap_t *, struct bpf_program *, char *, int, bpf_u_int32) = nullptr;
|
// FIXME: bridge between pcap_module and netdev_pcap
|
||||||
static int (*pcap_findalldevs_dl)(pcap_if_t **, char *) = nullptr;
|
static pcap_module *module = nullptr;
|
||||||
static pcap_t *(*pcap_open_live_dl)(const char *name, int, int, int, char *) = nullptr;
|
|
||||||
static int (*pcap_next_ex_dl)(pcap_t *, struct pcap_pkthdr **, const u_char **) = nullptr;
|
|
||||||
static void (*pcap_close_dl)(pcap_t *) = nullptr;
|
|
||||||
static int (*pcap_setfilter_dl)(pcap_t *, struct bpf_program *) = nullptr;
|
|
||||||
static int (*pcap_sendpacket_dl)(pcap_t *, u_char *, int) = nullptr;
|
|
||||||
static int (*pcap_set_datalink_dl)(pcap_t *, int) = nullptr;
|
|
||||||
static int (*pcap_dispatch_dl)(pcap_t *, int, pcap_handler callback, u_char *) = nullptr;
|
|
||||||
|
|
||||||
|
|
||||||
#if 0
|
|
||||||
#define pcap_compile_dl pcap_compile
|
|
||||||
#define pcap_findalldevs_dl pcap_findalldevs
|
|
||||||
#define pcap_open_live_dl pcap_open_live
|
|
||||||
#define pcap_next_ex_dl pcap_next_ex
|
|
||||||
#define pcap_close_dl pcap_close
|
|
||||||
#define pcap_setfilter_dl pcap_setfilter
|
|
||||||
#define pcap_sendpacket_dl pcap_sendpacket
|
|
||||||
#define pcap_set_datalink_dl pcap_set_datalink
|
|
||||||
#endif
|
|
||||||
|
|
||||||
#ifdef SDLMAME_MACOSX
|
#ifdef SDLMAME_MACOSX
|
||||||
struct netdev_pcap_context {
|
struct netdev_pcap_context {
|
||||||
@ -140,7 +140,7 @@ static void *netdev_pcap_blocker(void *arg) {
|
|||||||
struct netdev_pcap_context *ctx = (struct netdev_pcap_context*)arg;
|
struct netdev_pcap_context *ctx = (struct netdev_pcap_context*)arg;
|
||||||
|
|
||||||
while(ctx && ctx->p) {
|
while(ctx && ctx->p) {
|
||||||
pcap_dispatch_dl(ctx->p, 1, netdev_pcap_handler, (u_char*)ctx);
|
(*module->pcap_dispatch_dl)(ctx->p, 1, netdev_pcap_handler, (u_char*)ctx);
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0;
|
return 0;
|
||||||
@ -152,19 +152,19 @@ netdev_pcap::netdev_pcap(const char *name, class device_network_interface *ifdev
|
|||||||
{
|
{
|
||||||
char errbuf[PCAP_ERRBUF_SIZE];
|
char errbuf[PCAP_ERRBUF_SIZE];
|
||||||
#if defined(SDLMAME_WIN32) || defined(OSD_WINDOWS)
|
#if defined(SDLMAME_WIN32) || defined(OSD_WINDOWS)
|
||||||
m_p = pcap_open_live_dl(name, 65535, 1, -1, errbuf);
|
m_p = (*module->pcap_open_live_dl)(name, 65535, 1, -1, errbuf);
|
||||||
#else
|
#else
|
||||||
m_p = pcap_open_live_dl(name, 65535, 1, 1, errbuf);
|
m_p = (*module->pcap_open_live_dl)(name, 65535, 1, 1, errbuf);
|
||||||
#endif
|
#endif
|
||||||
if(!m_p)
|
if(!m_p)
|
||||||
{
|
{
|
||||||
osd_printf_error("Unable to open %s: %s\n", name, errbuf);
|
osd_printf_error("Unable to open %s: %s\n", name, errbuf);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
if(pcap_set_datalink_dl(m_p, DLT_EN10MB) == -1)
|
if ((*module->pcap_set_datalink_dl)(m_p, DLT_EN10MB) == -1)
|
||||||
{
|
{
|
||||||
osd_printf_error("Unable to set %s to ethernet", name);
|
osd_printf_error("Unable to set %s to ethernet", name);
|
||||||
pcap_close_dl(m_p);
|
(*module->pcap_close_dl)(m_p);
|
||||||
m_p = nullptr;
|
m_p = nullptr;
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -188,10 +188,10 @@ void netdev_pcap::set_mac(const char *mac)
|
|||||||
#else
|
#else
|
||||||
sprintf(filter, "ether dst %.2X:%.2X:%.2X:%.2X:%.2X:%.2X or ether multicast or ether broadcast", (unsigned char)mac[0], (unsigned char)mac[1], (unsigned char)mac[2],(unsigned char)mac[3], (unsigned char)mac[4], (unsigned char)mac[5]);
|
sprintf(filter, "ether dst %.2X:%.2X:%.2X:%.2X:%.2X:%.2X or ether multicast or ether broadcast", (unsigned char)mac[0], (unsigned char)mac[1], (unsigned char)mac[2],(unsigned char)mac[3], (unsigned char)mac[4], (unsigned char)mac[5]);
|
||||||
#endif
|
#endif
|
||||||
if(pcap_compile_dl(m_p, &fp, filter, 1, 0) == -1) {
|
if ((*module->pcap_compile_dl)(m_p, &fp, filter, 1, 0) == -1) {
|
||||||
osd_printf_error("Error with pcap_compile\n");
|
osd_printf_error("Error with pcap_compile\n");
|
||||||
}
|
}
|
||||||
if(pcap_setfilter_dl(m_p, &fp) == -1) {
|
if ((*module->pcap_setfilter_dl)(m_p, &fp) == -1) {
|
||||||
osd_printf_error("Error with pcap_setfilter\n");
|
osd_printf_error("Error with pcap_setfilter\n");
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -203,7 +203,7 @@ int netdev_pcap::send(UINT8 *buf, int len)
|
|||||||
printf("send invoked, but no pcap context\n");
|
printf("send invoked, but no pcap context\n");
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
ret = pcap_sendpacket_dl(m_p, buf, len);
|
ret = (*module->pcap_sendpacket_dl)(m_p, buf, len);
|
||||||
printf("sent packet length %d, returned %d\n", len, ret);
|
printf("sent packet length %d, returned %d\n", len, ret);
|
||||||
return ret ? len : 0;
|
return ret ? len : 0;
|
||||||
//return (!pcap_sendpacket_dl(m_p, buf, len))?len:0;
|
//return (!pcap_sendpacket_dl(m_p, buf, len))?len:0;
|
||||||
@ -228,7 +228,7 @@ int netdev_pcap::recv_dev(UINT8 **buf)
|
|||||||
#else
|
#else
|
||||||
struct pcap_pkthdr *header;
|
struct pcap_pkthdr *header;
|
||||||
if(!m_p) return 0;
|
if(!m_p) return 0;
|
||||||
return (pcap_next_ex_dl(m_p, &header, (const u_char **)buf) == 1)?header->len:0;
|
return ((*module->pcap_next_ex_dl)(m_p, &header, (const u_char **)buf) == 1)?header->len:0;
|
||||||
#endif
|
#endif
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -239,7 +239,7 @@ netdev_pcap::~netdev_pcap()
|
|||||||
pthread_cancel(m_thread);
|
pthread_cancel(m_thread);
|
||||||
pthread_join(m_thread, nullptr);
|
pthread_join(m_thread, nullptr);
|
||||||
#endif
|
#endif
|
||||||
if(m_p) pcap_close_dl(m_p);
|
if(m_p) (*module->pcap_close_dl)(m_p);
|
||||||
m_p = nullptr;
|
m_p = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -249,52 +249,16 @@ static CREATE_NETDEV(create_pcap)
|
|||||||
return dynamic_cast<osd_netdev *>(dev);
|
return dynamic_cast<osd_netdev *>(dev);
|
||||||
}
|
}
|
||||||
|
|
||||||
bool pcap_module::probe()
|
|
||||||
{
|
|
||||||
if (handle == nullptr)
|
|
||||||
{
|
|
||||||
handle = LoadDynamicLibrary(LIB_NAME);
|
|
||||||
return (handle != nullptr);
|
|
||||||
}
|
|
||||||
return true;
|
|
||||||
}
|
|
||||||
|
|
||||||
|
|
||||||
int pcap_module::init(const osd_options &options)
|
int pcap_module::init(const osd_options &options)
|
||||||
{
|
{
|
||||||
pcap_if_t *devs;
|
pcap_if_t *devs;
|
||||||
char errbuf[PCAP_ERRBUF_SIZE];
|
char errbuf[PCAP_ERRBUF_SIZE];
|
||||||
|
|
||||||
try
|
// FIXME: bridge between pcap_module and netdev_pcap
|
||||||
|
module = this;
|
||||||
|
|
||||||
|
if ((*pcap_findalldevs_dl)(&devs, errbuf) == -1)
|
||||||
{
|
{
|
||||||
if(!(pcap_findalldevs_dl = (int (*)(pcap_if_t **, char *))GetProcAddress(handle, "pcap_findalldevs")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_open_live_dl = (pcap_t* (*)(const char *, int, int, int, char *))GetProcAddress(handle, "pcap_open_live")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_next_ex_dl = (int (*)(pcap_t *, struct pcap_pkthdr **, const u_char **))GetProcAddress(handle, "pcap_next_ex")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_compile_dl = (int (*)(pcap_t *, struct bpf_program *, char *, int, bpf_u_int32))GetProcAddress(handle, "pcap_compile")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_close_dl = (void (*)(pcap_t *))GetProcAddress(handle, "pcap_close")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_setfilter_dl = (int (*)(pcap_t *, struct bpf_program *))GetProcAddress(handle, "pcap_setfilter")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_sendpacket_dl = (int (*)(pcap_t *, u_char *, int))GetProcAddress(handle, "pcap_sendpacket")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_set_datalink_dl = (int (*)(pcap_t *, int))GetProcAddress(handle, "pcap_set_datalink")))
|
|
||||||
throw GetLastError();
|
|
||||||
if(!(pcap_dispatch_dl = (int (*)(pcap_t *, int, pcap_handler callback, u_char *))GetProcAddress(handle, "pcap_dispatch")))
|
|
||||||
throw GetLastError();
|
|
||||||
}
|
|
||||||
catch (except_type e)
|
|
||||||
{
|
|
||||||
FreeLibrary(handle);
|
|
||||||
osd_printf_error(LIB_ERROR_STR, e);
|
|
||||||
return 1;
|
|
||||||
}
|
|
||||||
if(pcap_findalldevs_dl(&devs, errbuf) == -1)
|
|
||||||
{
|
|
||||||
FreeLibrary(handle);
|
|
||||||
osd_printf_error("Unable to get network devices: %s\n", errbuf);
|
osd_printf_error("Unable to get network devices: %s\n", errbuf);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@ -314,9 +278,8 @@ int pcap_module::init(const osd_options &options)
|
|||||||
void pcap_module::exit()
|
void pcap_module::exit()
|
||||||
{
|
{
|
||||||
clear_netdev();
|
clear_netdev();
|
||||||
//FreeLibrary(handle);
|
|
||||||
//handle = nullptr;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
#else
|
#else
|
||||||
#include "modules/osdmodule.h"
|
#include "modules/osdmodule.h"
|
||||||
#include "netdev_module.h"
|
#include "netdev_module.h"
|
||||||
|
@ -64,65 +64,27 @@ static inline void convert_present_params(const present_parameters *params, D3DP
|
|||||||
|
|
||||||
d3d_base *drawd3d9_init(void)
|
d3d_base *drawd3d9_init(void)
|
||||||
{
|
{
|
||||||
bool post_available = true;
|
|
||||||
|
|
||||||
// dynamically grab the create function from d3d9.dll
|
|
||||||
HINSTANCE dllhandle = LoadLibrary(TEXT("d3d9.dll"));
|
|
||||||
if (dllhandle == nullptr)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Direct3D: Unable to access d3d9.dll\n");
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
// import the create function
|
|
||||||
direct3dcreate9_ptr direct3dcreate9 = (direct3dcreate9_ptr)GetProcAddress(dllhandle, "Direct3DCreate9");
|
|
||||||
if (direct3dcreate9 == nullptr)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Direct3D: Unable to find Direct3DCreate9\n");
|
|
||||||
FreeLibrary(dllhandle);
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
// create our core direct 3d object
|
|
||||||
IDirect3D9 *d3d9 = (*direct3dcreate9)(D3D_SDK_VERSION);
|
|
||||||
if (d3d9 == nullptr)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Direct3D: Error attempting to initialize Direct3D9\n");
|
|
||||||
FreeLibrary(dllhandle);
|
|
||||||
return nullptr;
|
|
||||||
}
|
|
||||||
|
|
||||||
// dynamically grab the shader load function from d3dx9.dll
|
|
||||||
HINSTANCE fxhandle = nullptr;
|
|
||||||
for (int idx = 99; idx >= 0; idx--) // a shameful moogle
|
|
||||||
{
|
|
||||||
#ifdef UNICODE
|
|
||||||
wchar_t dllbuf[13];
|
|
||||||
wsprintf(dllbuf, TEXT("d3dx9_%d.dll"), idx);
|
|
||||||
fxhandle = LoadLibrary(dllbuf);
|
|
||||||
#else
|
|
||||||
char dllbuf[13];
|
|
||||||
sprintf(dllbuf, "d3dx9_%d.dll", idx);
|
|
||||||
fxhandle = LoadLibraryA(dllbuf);
|
|
||||||
#endif
|
|
||||||
if (fxhandle != nullptr)
|
|
||||||
{
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
if (fxhandle == nullptr)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Direct3D: Warning - Unable find any D3D9 DLLs; disabling post-effect rendering\n");
|
|
||||||
post_available = false;
|
|
||||||
}
|
|
||||||
|
|
||||||
// allocate an object to hold our data
|
// allocate an object to hold our data
|
||||||
auto d3dptr = global_alloc(d3d_base);
|
d3d_base *d3dptr = global_alloc(d3d_base);
|
||||||
|
|
||||||
|
d3dptr->d3d9_dll = osd::dynamic_module::open({ "d3d9.dll" });
|
||||||
|
|
||||||
|
d3d9_create_fn d3d9_create_ptr = d3dptr->d3d9_dll->bind<d3d9_create_fn>("Direct3DCreate9");
|
||||||
|
if (d3d9_create_ptr == nullptr)
|
||||||
|
{
|
||||||
|
osd_printf_verbose("Direct3D: Unable to find Direct3D 9 runtime library\n");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
|
d3dptr->d3dobj = (*d3d9_create_ptr)(D3D_SDK_VERSION);
|
||||||
|
if (d3dptr->d3dobj == nullptr)
|
||||||
|
{
|
||||||
|
osd_printf_verbose("Direct3D: Unable to initialize Direct3D 9\n");
|
||||||
|
return true;
|
||||||
|
}
|
||||||
|
|
||||||
d3dptr->version = 9;
|
d3dptr->version = 9;
|
||||||
d3dptr->d3dobj = d3d9;
|
d3dptr->post_fx_available = true;
|
||||||
d3dptr->dllhandle = dllhandle;
|
|
||||||
d3dptr->post_fx_available = post_available;
|
|
||||||
d3dptr->libhandle = fxhandle;
|
|
||||||
set_interfaces(d3dptr);
|
set_interfaces(d3dptr);
|
||||||
|
|
||||||
osd_printf_verbose("Direct3D: Using Direct3D 9\n");
|
osd_printf_verbose("Direct3D: Using Direct3D 9\n");
|
||||||
@ -239,7 +201,6 @@ static ULONG release(d3d_base *d3dptr)
|
|||||||
{
|
{
|
||||||
IDirect3D9 *d3d9 = (IDirect3D9 *)d3dptr->d3dobj;
|
IDirect3D9 *d3d9 = (IDirect3D9 *)d3dptr->d3dobj;
|
||||||
ULONG result = IDirect3D9_Release(d3d9);
|
ULONG result = IDirect3D9_Release(d3d9);
|
||||||
FreeLibrary(d3dptr->dllhandle);
|
|
||||||
global_free(d3dptr);
|
global_free(d3dptr);
|
||||||
return result;
|
return result;
|
||||||
}
|
}
|
||||||
|
@ -64,7 +64,6 @@ public:
|
|||||||
{ }
|
{ }
|
||||||
|
|
||||||
d3d_texture_manager(renderer_d3d9 *d3d);
|
d3d_texture_manager(renderer_d3d9 *d3d);
|
||||||
~d3d_texture_manager();
|
|
||||||
|
|
||||||
void update_textures();
|
void update_textures();
|
||||||
|
|
||||||
@ -142,9 +141,9 @@ public:
|
|||||||
int get_cur_frame() const { return m_cur_frame; }
|
int get_cur_frame() const { return m_cur_frame; }
|
||||||
int get_prev_frame() const { return m_prev_frame; }
|
int get_prev_frame() const { return m_prev_frame; }
|
||||||
|
|
||||||
texture * get_tex() const { return m_d3dtex; }
|
IDirect3DTexture9 * get_tex() const { return m_d3dtex; }
|
||||||
surface * get_surface() const { return m_d3dsurface; }
|
IDirect3DSurface9 * get_surface() const { return m_d3dsurface; }
|
||||||
texture * get_finaltex() const { return m_d3dfinaltex; }
|
IDirect3DTexture9 * get_finaltex() const { return m_d3dfinaltex; }
|
||||||
|
|
||||||
vec2f & get_uvstart() { return m_start; }
|
vec2f & get_uvstart() { return m_start; }
|
||||||
vec2f & get_uvstop() { return m_stop; }
|
vec2f & get_uvstop() { return m_stop; }
|
||||||
@ -173,9 +172,9 @@ private:
|
|||||||
int m_xprescale, m_yprescale; // X/Y prescale factor
|
int m_xprescale, m_yprescale; // X/Y prescale factor
|
||||||
int m_cur_frame; // what is our current frame?
|
int m_cur_frame; // what is our current frame?
|
||||||
int m_prev_frame; // what was our last frame? (used to determine pause state)
|
int m_prev_frame; // what was our last frame? (used to determine pause state)
|
||||||
texture * m_d3dtex; // Direct3D texture pointer
|
IDirect3DTexture9 * m_d3dtex; // Direct3D texture pointer
|
||||||
surface * m_d3dsurface; // Direct3D offscreen plain surface pointer
|
IDirect3DSurface9 * m_d3dsurface; // Direct3D offscreen plain surface pointer
|
||||||
texture * m_d3dfinaltex; // Direct3D final (post-scaled) texture
|
IDirect3DTexture9 * m_d3dfinaltex; // Direct3D final (post-scaled) texture
|
||||||
};
|
};
|
||||||
|
|
||||||
/* poly_info holds information about a single polygon/d3d primitive */
|
/* poly_info holds information about a single polygon/d3d primitive */
|
||||||
@ -254,8 +253,8 @@ public:
|
|||||||
|
|
||||||
bool init(renderer_d3d9 *d3d, d3d_base *d3dintf, int source_width, int source_height, int target_width, int target_height);
|
bool init(renderer_d3d9 *d3d, d3d_base *d3dintf, int source_width, int source_height, int target_width, int target_height);
|
||||||
|
|
||||||
surface *last_target;
|
IDirect3DSurface9 *last_target;
|
||||||
texture *last_texture;
|
IDirect3DTexture9 *last_texture;
|
||||||
|
|
||||||
int target_width;
|
int target_width;
|
||||||
int target_height;
|
int target_height;
|
||||||
@ -293,16 +292,16 @@ public:
|
|||||||
int screen_index;
|
int screen_index;
|
||||||
int page_index;
|
int page_index;
|
||||||
|
|
||||||
surface *target_surface[2];
|
IDirect3DSurface9 *target_surface[2];
|
||||||
texture *target_texture[2];
|
IDirect3DTexture9 *target_texture[2];
|
||||||
surface *source_surface[2];
|
IDirect3DSurface9 *source_surface[2];
|
||||||
texture *source_texture[2];
|
IDirect3DTexture9 *source_texture[2];
|
||||||
|
|
||||||
d3d_render_target *next;
|
d3d_render_target *next;
|
||||||
d3d_render_target *prev;
|
d3d_render_target *prev;
|
||||||
|
|
||||||
surface *bloom_surface[MAX_BLOOM_COUNT];
|
IDirect3DSurface9 *bloom_surface[MAX_BLOOM_COUNT];
|
||||||
texture *bloom_texture[MAX_BLOOM_COUNT];
|
IDirect3DTexture9 *bloom_texture[MAX_BLOOM_COUNT];
|
||||||
|
|
||||||
float bloom_dims[MAX_BLOOM_COUNT][2];
|
float bloom_dims[MAX_BLOOM_COUNT][2];
|
||||||
|
|
||||||
|
@ -2,18 +2,10 @@
|
|||||||
// copyright-holders:Aaron Giles
|
// copyright-holders:Aaron Giles
|
||||||
//============================================================
|
//============================================================
|
||||||
//
|
//
|
||||||
// d3dhlsl.c - Win32 Direct3D HLSL implementation
|
// d3dhlsl.cpp - Win32 Direct3D HLSL implementation
|
||||||
//
|
//
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
// Useful info:
|
|
||||||
// Windows XP/2003 shipped with DirectX 8.1
|
|
||||||
// Windows 2000 shipped with DirectX 7a
|
|
||||||
// Windows 98SE shipped with DirectX 6.1a
|
|
||||||
// Windows 98 shipped with DirectX 5
|
|
||||||
// Windows NT shipped with DirectX 3.0a
|
|
||||||
// Windows 95 shipped with DirectX 2
|
|
||||||
|
|
||||||
// MAME headers
|
// MAME headers
|
||||||
#include "emu.h"
|
#include "emu.h"
|
||||||
#include "drivenum.h"
|
#include "drivenum.h"
|
||||||
@ -46,14 +38,6 @@
|
|||||||
static void get_vector(const char *data, int count, float *out, bool report_error);
|
static void get_vector(const char *data, int count, float *out, bool report_error);
|
||||||
|
|
||||||
|
|
||||||
//============================================================
|
|
||||||
// TYPE DEFINITIONS
|
|
||||||
//============================================================
|
|
||||||
|
|
||||||
typedef HRESULT (WINAPI *direct3dx9_loadeffect_ptr)(LPDIRECT3DDEVICE9 pDevice, LPCTSTR pSrcFile, const D3DXMACRO *pDefines, LPD3DXINCLUDE pInclude, DWORD Flags, LPD3DXEFFECTPOOL pPool, LPD3DXEFFECT *ppEffect, LPD3DXBUFFER *ppCompilationErrors);
|
|
||||||
static direct3dx9_loadeffect_ptr g_load_effect = nullptr;
|
|
||||||
|
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// shader manager constructor
|
// shader manager constructor
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -119,21 +103,21 @@ void shaders::window_save()
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.create_texture)(d3d->get_device(), snap_width, snap_height, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &snap_copy_texture);
|
HRESULT result = d3d->get_device()->CreateTexture(snap_width, snap_height, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &snap_copy_texture, nullptr);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Unable to init system-memory target for HLSL snapshot (%08x), bailing\n", (UINT32)result);
|
osd_printf_verbose("Direct3D: Unable to init system-memory target for HLSL snapshot (%08x), bailing\n", (UINT32)result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
(*d3dintf->texture.get_surface_level)(snap_copy_texture, 0, &snap_copy_target);
|
snap_copy_texture->GetSurfaceLevel(0, &snap_copy_target);
|
||||||
|
|
||||||
result = (*d3dintf->device.create_texture)(d3d->get_device(), snap_width, snap_height, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &snap_texture);
|
result = d3d->get_device()->CreateTexture(snap_width, snap_height, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &snap_texture, nullptr);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Unable to init video-memory target for HLSL snapshot (%08x), bailing\n", (UINT32)result);
|
osd_printf_verbose("Direct3D: Unable to init video-memory target for HLSL snapshot (%08x), bailing\n", (UINT32)result);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
(*d3dintf->texture.get_surface_level)(snap_texture, 0, &snap_target);
|
snap_texture->GetSurfaceLevel(0, &snap_target);
|
||||||
|
|
||||||
render_snap = true;
|
render_snap = true;
|
||||||
snap_rendered = false;
|
snap_rendered = false;
|
||||||
@ -169,7 +153,7 @@ void shaders::window_record()
|
|||||||
// shaders::avi_update_snap
|
// shaders::avi_update_snap
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
void shaders::avi_update_snap(surface *surface)
|
void shaders::avi_update_snap(IDirect3DSurface9 *surface)
|
||||||
{
|
{
|
||||||
if (!master_enable || !d3dintf->post_fx_available)
|
if (!master_enable || !d3dintf->post_fx_available)
|
||||||
{
|
{
|
||||||
@ -185,15 +169,15 @@ void shaders::avi_update_snap(surface *surface)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// copy the texture
|
// copy the texture
|
||||||
HRESULT result = (*d3dintf->device.get_render_target_data)(d3d->get_device(), surface, avi_copy_surface);
|
HRESULT result = d3d->get_device()->GetRenderTargetData(surface, avi_copy_surface);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// lock the texture
|
// lock the texture
|
||||||
result = (*d3dintf->surface.lock_rect)(avi_copy_surface, &rect, nullptr, D3DLOCK_DISCARD);
|
result = avi_copy_surface->LockRect(&rect, nullptr, D3DLOCK_DISCARD);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -211,11 +195,9 @@ void shaders::avi_update_snap(surface *surface)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// unlock
|
// unlock
|
||||||
result = (*d3dintf->surface.unlock_rect)(avi_copy_surface);
|
result = avi_copy_surface->UnlockRect();
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
osd_printf_verbose("Direct3D: Error %08lX during texture UnlockRect call\n", result);
|
||||||
osd_printf_verbose("Direct3D: Error %08X during texture unlock_rect call\n", (int)result);
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
@ -224,7 +206,7 @@ void shaders::avi_update_snap(surface *surface)
|
|||||||
// hlsl_render_snapshot
|
// hlsl_render_snapshot
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
void shaders::render_snapshot(surface *surface)
|
void shaders::render_snapshot(IDirect3DSurface9 *surface)
|
||||||
{
|
{
|
||||||
if (!master_enable || !d3dintf->post_fx_available)
|
if (!master_enable || !d3dintf->post_fx_available)
|
||||||
{
|
{
|
||||||
@ -242,15 +224,15 @@ void shaders::render_snapshot(surface *surface)
|
|||||||
}
|
}
|
||||||
|
|
||||||
// copy the texture
|
// copy the texture
|
||||||
HRESULT result = (*d3dintf->device.get_render_target_data)(d3d->get_device(), surface, snap_copy_target);
|
HRESULT result = d3d->get_device()->GetRenderTargetData(surface, snap_copy_target);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
// lock the texture
|
// lock the texture
|
||||||
result = (*d3dintf->surface.lock_rect)(snap_copy_target, &rect, nullptr, D3DLOCK_DISCARD);
|
result = snap_copy_target->LockRect(&rect, nullptr, D3DLOCK_DISCARD);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
@ -292,30 +274,31 @@ void shaders::render_snapshot(surface *surface)
|
|||||||
png_free(&pnginfo);
|
png_free(&pnginfo);
|
||||||
|
|
||||||
// unlock
|
// unlock
|
||||||
result = (*d3dintf->surface.unlock_rect)(snap_copy_target);
|
result = snap_copy_target->UnlockRect();
|
||||||
if (result != D3D_OK) osd_printf_verbose("Direct3D: Error %08X during texture unlock_rect call\n", (int)result);
|
if (FAILED(result))
|
||||||
|
osd_printf_verbose("Direct3D: Error %08lX during texture UnlockRect call\n", result);
|
||||||
|
|
||||||
if (snap_texture != nullptr)
|
if (snap_texture != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->texture.release)(snap_texture);
|
snap_texture->Release();
|
||||||
snap_texture = nullptr;
|
snap_texture = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (snap_target != nullptr)
|
if (snap_target != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->surface.release)(snap_target);
|
snap_target->Release();
|
||||||
snap_target = nullptr;
|
snap_target = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (snap_copy_texture != nullptr)
|
if (snap_copy_texture != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->texture.release)(snap_copy_texture);
|
snap_copy_texture->Release();
|
||||||
snap_copy_texture = nullptr;
|
snap_copy_texture = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (snap_copy_target != nullptr)
|
if (snap_copy_target != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->surface.release)(snap_copy_target);
|
snap_copy_target->Release();
|
||||||
snap_copy_target = nullptr;
|
snap_copy_target = nullptr;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -332,7 +315,7 @@ void shaders::record_texture()
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
surface *surface = avi_final_target;
|
IDirect3DSurface9 *surface = avi_final_target;
|
||||||
|
|
||||||
// ignore if nothing to do
|
// ignore if nothing to do
|
||||||
if (avi_output_file == nullptr || surface == nullptr)
|
if (avi_output_file == nullptr || surface == nullptr)
|
||||||
@ -621,20 +604,17 @@ void shaders::set_texture(texture_info *texture)
|
|||||||
|
|
||||||
void shaders::init(d3d_base *d3dintf, running_machine *machine, renderer_d3d9 *renderer)
|
void shaders::init(d3d_base *d3dintf, running_machine *machine, renderer_d3d9 *renderer)
|
||||||
{
|
{
|
||||||
if (!d3dintf->post_fx_available)
|
d3dx9_dll = osd::dynamic_module::open({ "d3dx9_43.dll" });
|
||||||
{
|
|
||||||
return;
|
|
||||||
}
|
|
||||||
|
|
||||||
g_load_effect = (direct3dx9_loadeffect_ptr)GetProcAddress(d3dintf->libhandle, "D3DXCreateEffectFromFileW");
|
d3dx_create_effect_from_file_ptr = d3dx9_dll->bind<d3dx_create_effect_from_file_fn>("D3DXCreateEffectFromFileW");
|
||||||
if (g_load_effect == nullptr)
|
if (!d3dx_create_effect_from_file_ptr)
|
||||||
{
|
{
|
||||||
printf("Direct3D: Unable to find D3DXCreateEffectFromFileW\n");
|
printf("Direct3D: Unable to find D3DXCreateEffectFromFileW\n");
|
||||||
d3dintf->post_fx_available = false;
|
d3dintf->post_fx_available = false;
|
||||||
|
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
d3dintf->post_fx_available = true;
|
||||||
this->d3dintf = d3dintf;
|
this->d3dintf = d3dintf;
|
||||||
this->machine = machine;
|
this->machine = machine;
|
||||||
this->d3d = renderer;
|
this->d3d = renderer;
|
||||||
@ -837,41 +817,44 @@ int shaders::create_resources(bool reset, std::vector<ui::menu_item>& sliders)
|
|||||||
options = &last_options;
|
options = &last_options;
|
||||||
}
|
}
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.get_render_target)(d3d->get_device(), 0, &backbuffer);
|
HRESULT result = d3d->get_device()->GetRenderTarget(0, &backbuffer);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device get_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device GetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
|
|
||||||
result = (*d3dintf->device.create_texture)(d3d->get_device(), 4, 4, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &black_texture);
|
result = d3d->get_device()->CreateTexture(4, 4, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &black_texture, nullptr);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Unable to init video-memory target for black texture (%08x)\n", (UINT32)result);
|
osd_printf_verbose("Direct3D: Unable to init video-memory target for black texture (%08x)\n", (UINT32)result);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
(*d3dintf->texture.get_surface_level)(black_texture, 0, &black_surface);
|
black_texture->GetSurfaceLevel(0, &black_surface);
|
||||||
result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, black_surface);
|
result = d3d->get_device()->SetRenderTarget(0, black_surface);
|
||||||
if (result != D3D_OK) osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
if (FAILED(result))
|
||||||
result = (*d3dintf->device.clear)(d3d->get_device(), 0, nullptr, D3DCLEAR_TARGET, D3DCOLOR_ARGB(0,0,0,0), 0, 0);
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
if (result != D3D_OK) osd_printf_verbose("Direct3D: Error %08X during device clear call\n", (int)result);
|
result = d3d->get_device()->Clear(0, nullptr, D3DCLEAR_TARGET, D3DCOLOR_ARGB(0,0,0,0), 0, 0);
|
||||||
result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, backbuffer);
|
if (FAILED(result))
|
||||||
if (result != D3D_OK) osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device clear call\n", result);
|
||||||
|
result = d3d->get_device()->SetRenderTarget(0, backbuffer);
|
||||||
|
if (FAILED(result))
|
||||||
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
|
|
||||||
result = (*d3dintf->device.create_texture)(d3d->get_device(), (int)snap_width, (int)snap_height, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &avi_copy_texture);
|
result = d3d->get_device()->CreateTexture((int)snap_width, (int)snap_height, 1, D3DUSAGE_DYNAMIC, D3DFMT_A8R8G8B8, D3DPOOL_SYSTEMMEM, &avi_copy_texture, nullptr);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Unable to init system-memory target for HLSL AVI dumping (%08x)\n", (UINT32)result);
|
osd_printf_verbose("Direct3D: Unable to init system-memory target for HLSL AVI dumping (%08x)\n", (UINT32)result);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
(*d3dintf->texture.get_surface_level)(avi_copy_texture, 0, &avi_copy_surface);
|
avi_copy_texture->GetSurfaceLevel(0, &avi_copy_surface);
|
||||||
|
|
||||||
result = (*d3dintf->device.create_texture)(d3d->get_device(), (int)snap_width, (int)snap_height, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &avi_final_texture);
|
result = d3d->get_device()->CreateTexture((int)snap_width, (int)snap_height, 1, D3DUSAGE_RENDERTARGET, D3DFMT_A8R8G8B8, D3DPOOL_DEFAULT, &avi_final_texture, nullptr);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Unable to init video-memory target for HLSL AVI dumping (%08x)\n", (UINT32)result);
|
osd_printf_verbose("Direct3D: Unable to init video-memory target for HLSL AVI dumping (%08x)\n", (UINT32)result);
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
(*d3dintf->texture.get_surface_level)(avi_final_texture, 0, &avi_final_target);
|
avi_final_texture->GetSurfaceLevel(0, &avi_final_target);
|
||||||
|
|
||||||
emu_file file(machine->options().art_path(), OPEN_FLAG_READ);
|
emu_file file(machine->options().art_path(), OPEN_FLAG_READ);
|
||||||
render_load_png(shadow_bitmap, file, nullptr, options->shadow_mask_texture);
|
render_load_png(shadow_bitmap, file, nullptr, options->shadow_mask_texture);
|
||||||
@ -890,7 +873,7 @@ int shaders::create_resources(bool reset, std::vector<ui::menu_item>& sliders)
|
|||||||
texture.seqid = 0;
|
texture.seqid = 0;
|
||||||
|
|
||||||
// now create it (no prescale, no wrap)
|
// now create it (no prescale, no wrap)
|
||||||
shadow_texture = new texture_info(d3d->get_texture_manager(), &texture, 1, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXFORMAT(TEXFORMAT_ARGB32));
|
shadow_texture = global_alloc(texture_info(d3d->get_texture_manager(), &texture, 1, PRIMFLAG_BLENDMODE(BLENDMODE_ALPHA) | PRIMFLAG_TEXFORMAT(TEXFORMAT_ARGB32)));
|
||||||
}
|
}
|
||||||
|
|
||||||
const char *fx_dir = downcast<windows_options &>(machine->options()).screen_post_fx_dir();
|
const char *fx_dir = downcast<windows_options &>(machine->options()).screen_post_fx_dir();
|
||||||
@ -1035,10 +1018,10 @@ void shaders::begin_draw()
|
|||||||
downsample_effect->set_technique("DefaultTechnique");
|
downsample_effect->set_technique("DefaultTechnique");
|
||||||
vector_effect->set_technique("DefaultTechnique");
|
vector_effect->set_technique("DefaultTechnique");
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.get_render_target)(d3d->get_device(), 0, &backbuffer);
|
HRESULT result = d3d->get_device()->GetRenderTarget(0, &backbuffer);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device get_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device GetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1058,7 +1041,7 @@ void shaders::begin_frame()
|
|||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
void shaders::blit(
|
void shaders::blit(
|
||||||
surface *dst,
|
IDirect3DSurface9 *dst,
|
||||||
bool clear_dst,
|
bool clear_dst,
|
||||||
D3DPRIMITIVETYPE prim_type,
|
D3DPRIMITIVETYPE prim_type,
|
||||||
UINT32 prim_index,
|
UINT32 prim_index,
|
||||||
@ -1068,18 +1051,18 @@ void shaders::blit(
|
|||||||
|
|
||||||
if (dst != nullptr)
|
if (dst != nullptr)
|
||||||
{
|
{
|
||||||
result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, dst);
|
result = d3d->get_device()->SetRenderTarget(0, dst);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (clear_dst)
|
if (clear_dst)
|
||||||
{
|
{
|
||||||
result = (*d3dintf->device.clear)(d3d->get_device(), 0, nullptr, D3DCLEAR_TARGET, D3DCOLOR_ARGB(1,0,0,0), 0, 0);
|
result = d3d->get_device()->Clear(0, nullptr, D3DCLEAR_TARGET, D3DCOLOR_ARGB(1,0,0,0), 0, 0);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device clear call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device clear call\n", result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
@ -1092,10 +1075,10 @@ void shaders::blit(
|
|||||||
curr_effect->begin_pass(pass);
|
curr_effect->begin_pass(pass);
|
||||||
|
|
||||||
// add the primitives
|
// add the primitives
|
||||||
result = (*d3dintf->device.draw_primitive)(d3d->get_device(), prim_type, prim_index, prim_count);
|
result = d3d->get_device()->DrawPrimitive(prim_type, prim_index, prim_count);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device draw_primitive call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device DrawPrimitive call\n", result);
|
||||||
}
|
}
|
||||||
|
|
||||||
curr_effect->end_pass();
|
curr_effect->end_pass();
|
||||||
@ -1565,10 +1548,10 @@ int shaders::screen_pass(d3d_render_target *rt, int source_index, poly_info *pol
|
|||||||
{
|
{
|
||||||
blit(avi_final_target, false, poly->get_type(), vertnum, poly->get_count());
|
blit(avi_final_target, false, poly->get_type(), vertnum, poly->get_count());
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, backbuffer);
|
HRESULT result = d3d->get_device()->SetRenderTarget(0, backbuffer);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -1576,10 +1559,10 @@ int shaders::screen_pass(d3d_render_target *rt, int source_index, poly_info *pol
|
|||||||
{
|
{
|
||||||
blit(snap_target, false, poly->get_type(), vertnum, poly->get_count());
|
blit(snap_target, false, poly->get_type(), vertnum, poly->get_count());
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, backbuffer);
|
HRESULT result = d3d->get_device()->SetRenderTarget(0, backbuffer);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
|
|
||||||
snap_rendered = true;
|
snap_rendered = true;
|
||||||
@ -1684,10 +1667,10 @@ void shaders::render_quad(poly_info *poly, int vertnum)
|
|||||||
|
|
||||||
next_index = vector_pass(rt, next_index, poly, vertnum);
|
next_index = vector_pass(rt, next_index, poly, vertnum);
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, backbuffer);
|
HRESULT result = d3d->get_device()->SetRenderTarget(0, backbuffer);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
else if (PRIMFLAG_GET_VECTORBUF(poly->get_flags()) && vector_enable)
|
else if (PRIMFLAG_GET_VECTORBUF(poly->get_flags()) && vector_enable)
|
||||||
@ -1736,10 +1719,10 @@ void shaders::render_quad(poly_info *poly, int vertnum)
|
|||||||
next_index = screen_pass(rt, next_index, poly, vertnum);
|
next_index = screen_pass(rt, next_index, poly, vertnum);
|
||||||
d3d->set_wrap(PRIMFLAG_GET_TEXWRAP(curr_texture->get_flags()) ? D3DTADDRESS_WRAP : D3DTADDRESS_CLAMP);
|
d3d->set_wrap(PRIMFLAG_GET_TEXWRAP(curr_texture->get_flags()) ? D3DTADDRESS_WRAP : D3DTADDRESS_CLAMP);
|
||||||
|
|
||||||
HRESULT result = (*d3dintf->device.set_render_target)(d3d->get_device(), 0, backbuffer);
|
HRESULT result = d3d->get_device()->SetRenderTarget(0, backbuffer);
|
||||||
if (result != D3D_OK)
|
if (FAILED(result))
|
||||||
{
|
{
|
||||||
osd_printf_verbose("Direct3D: Error %08X during device set_render_target call\n", (int)result);
|
osd_printf_verbose("Direct3D: Error %08lX during device SetRenderTarget call\n", result);
|
||||||
}
|
}
|
||||||
|
|
||||||
lines_pending = false;
|
lines_pending = false;
|
||||||
@ -1770,13 +1753,14 @@ void shaders::end_draw()
|
|||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
|
|
||||||
(*d3dintf->surface.release)(backbuffer);
|
backbuffer->Release();
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// shaders::add_cache_target - register a cache target
|
// shaders::add_cache_target - register a cache target
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
bool shaders::add_cache_target(renderer_d3d9* d3d, texture_info* texture, int source_width, int source_height, int target_width, int target_height, int screen_index)
|
bool shaders::add_cache_target(renderer_d3d9* d3d, texture_info* texture, int source_width, int source_height, int target_width, int target_height, int screen_index)
|
||||||
{
|
{
|
||||||
cache_target* target = (cache_target*)global_alloc_clear<cache_target>();
|
cache_target* target = (cache_target*)global_alloc_clear<cache_target>();
|
||||||
@ -1803,6 +1787,7 @@ bool shaders::add_cache_target(renderer_d3d9* d3d, texture_info* texture, int so
|
|||||||
//============================================================
|
//============================================================
|
||||||
// shaders::get_texture_target(render_primitive::prim, texture_info::texture)
|
// shaders::get_texture_target(render_primitive::prim, texture_info::texture)
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
d3d_render_target* shaders::get_texture_target(render_primitive *prim, texture_info *texture)
|
d3d_render_target* shaders::get_texture_target(render_primitive *prim, texture_info *texture)
|
||||||
{
|
{
|
||||||
auto win = d3d->assert_window();
|
auto win = d3d->assert_window();
|
||||||
@ -2108,42 +2093,42 @@ void shaders::delete_resources(bool reset)
|
|||||||
|
|
||||||
if (backbuffer != nullptr)
|
if (backbuffer != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->surface.release)(backbuffer);
|
backbuffer->Release();
|
||||||
backbuffer = nullptr;
|
backbuffer = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (black_surface != nullptr)
|
if (black_surface != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->surface.release)(black_surface);
|
black_surface->Release();
|
||||||
black_surface = nullptr;
|
black_surface = nullptr;
|
||||||
}
|
}
|
||||||
if (black_texture != nullptr)
|
if (black_texture != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->texture.release)(black_texture);
|
black_texture->Release();
|
||||||
black_texture = nullptr;
|
black_texture = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (avi_copy_texture != nullptr)
|
if (avi_copy_texture != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->texture.release)(avi_copy_texture);
|
avi_copy_texture->Release();
|
||||||
avi_copy_texture = nullptr;
|
avi_copy_texture = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (avi_copy_surface != nullptr)
|
if (avi_copy_surface != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->surface.release)(avi_copy_surface);
|
avi_copy_surface->Release();
|
||||||
avi_copy_surface = nullptr;
|
avi_copy_surface = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (avi_final_texture != nullptr)
|
if (avi_final_texture != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->texture.release)(avi_final_texture);
|
avi_final_texture->Release();
|
||||||
avi_final_texture = nullptr;
|
avi_final_texture = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (avi_final_target != nullptr)
|
if (avi_final_target != nullptr)
|
||||||
{
|
{
|
||||||
(*d3dintf->surface.release)(avi_final_target);
|
avi_final_target->Release();
|
||||||
avi_final_target = nullptr;
|
avi_final_target = nullptr;
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -2909,12 +2894,12 @@ void uniform::set(bool x)
|
|||||||
m_bval = x;
|
m_bval = x;
|
||||||
}
|
}
|
||||||
|
|
||||||
void uniform::set(matrix *mat)
|
void uniform::set(D3DMATRIX *mat)
|
||||||
{
|
{
|
||||||
m_mval = mat;
|
m_mval = mat;
|
||||||
}
|
}
|
||||||
|
|
||||||
void uniform::set(texture *tex)
|
void uniform::set(IDirect3DTexture9 *tex)
|
||||||
{
|
{
|
||||||
m_texture = tex;
|
m_texture = tex;
|
||||||
}
|
}
|
||||||
@ -2951,9 +2936,8 @@ void uniform::upload()
|
|||||||
// effect functions
|
// effect functions
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
effect::effect(shaders *shadersys, device *dev, const char *name, const char *path)
|
effect::effect(shaders *shadersys, IDirect3DDevice9 *dev, const char *name, const char *path)
|
||||||
{
|
{
|
||||||
IDirect3DDevice9 *device = (IDirect3DDevice9 *)dev;
|
|
||||||
LPD3DXBUFFER buffer_errors = nullptr;
|
LPD3DXBUFFER buffer_errors = nullptr;
|
||||||
|
|
||||||
m_shaders = shadersys;
|
m_shaders = shadersys;
|
||||||
@ -2966,7 +2950,7 @@ effect::effect(shaders *shadersys, device *dev, const char *name, const char *pa
|
|||||||
sprintf(name_cstr, "%s\\%s", path, name);
|
sprintf(name_cstr, "%s\\%s", path, name);
|
||||||
TCHAR *effect_name = tstring_from_utf8(name_cstr);
|
TCHAR *effect_name = tstring_from_utf8(name_cstr);
|
||||||
|
|
||||||
HRESULT hr = (*g_load_effect)(device, effect_name, nullptr, nullptr, 0, nullptr, &m_effect, &buffer_errors);
|
HRESULT hr = (*shadersys->d3dx_create_effect_from_file_ptr)(dev, effect_name, nullptr, nullptr, 0, nullptr, &m_effect, &buffer_errors);
|
||||||
if (FAILED(hr))
|
if (FAILED(hr))
|
||||||
{
|
{
|
||||||
if (buffer_errors != nullptr)
|
if (buffer_errors != nullptr)
|
||||||
@ -3093,14 +3077,14 @@ void effect::set_bool(D3DXHANDLE param, bool value)
|
|||||||
m_effect->SetBool(param, value);
|
m_effect->SetBool(param, value);
|
||||||
}
|
}
|
||||||
|
|
||||||
void effect::set_matrix(D3DXHANDLE param, matrix *matrix)
|
void effect::set_matrix(D3DXHANDLE param, D3DMATRIX *matrix)
|
||||||
{
|
{
|
||||||
m_effect->SetMatrix(param, (D3DXMATRIX*)matrix);
|
m_effect->SetMatrix(param, (D3DXMATRIX*)matrix);
|
||||||
}
|
}
|
||||||
|
|
||||||
void effect::set_texture(D3DXHANDLE param, texture *tex)
|
void effect::set_texture(D3DXHANDLE param, IDirect3DTexture9 *tex)
|
||||||
{
|
{
|
||||||
m_effect->SetTexture(param, (IDirect3DTexture9*)tex);
|
m_effect->SetTexture(param, tex);
|
||||||
}
|
}
|
||||||
|
|
||||||
D3DXHANDLE effect::get_parameter(D3DXHANDLE param, const char *name)
|
D3DXHANDLE effect::get_parameter(D3DXHANDLE param, const char *name)
|
||||||
|
@ -13,16 +13,15 @@
|
|||||||
#include "aviio.h"
|
#include "aviio.h"
|
||||||
#include "../frontend/mame/ui/menuitem.h"
|
#include "../frontend/mame/ui/menuitem.h"
|
||||||
#include "../frontend/mame/ui/slider.h"
|
#include "../frontend/mame/ui/slider.h"
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
//============================================================
|
|
||||||
// CONSTANTS
|
|
||||||
//============================================================
|
|
||||||
|
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// TYPE DEFINITIONS
|
// TYPE DEFINITIONS
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
|
// Typedefs for dynamically loaded functions
|
||||||
|
typedef HRESULT (*d3dx_create_effect_from_file_fn)(LPDIRECT3DDEVICE9, LPCTSTR, const D3DXMACRO *, LPD3DXINCLUDE, DWORD, LPD3DXEFFECTPOOL, LPD3DXEFFECT *, LPD3DXBUFFER *);
|
||||||
|
|
||||||
class effect;
|
class effect;
|
||||||
class shaders;
|
class shaders;
|
||||||
|
|
||||||
@ -115,8 +114,8 @@ public:
|
|||||||
void set(float x);
|
void set(float x);
|
||||||
void set(int x);
|
void set(int x);
|
||||||
void set(bool x);
|
void set(bool x);
|
||||||
void set(matrix *mat);
|
void set(D3DMATRIX *mat);
|
||||||
void set(texture *tex);
|
void set(IDirect3DTexture9 *tex);
|
||||||
|
|
||||||
void upload();
|
void upload();
|
||||||
void update();
|
void update();
|
||||||
@ -127,10 +126,10 @@ protected:
|
|||||||
float m_vec[4];
|
float m_vec[4];
|
||||||
int m_ival;
|
int m_ival;
|
||||||
bool m_bval;
|
bool m_bval;
|
||||||
matrix *m_mval;
|
D3DMATRIX *m_mval;
|
||||||
texture *m_texture;
|
IDirect3DTexture9 *m_texture;
|
||||||
int m_count;
|
int m_count;
|
||||||
uniform_type m_type;
|
uniform_type m_type;
|
||||||
int m_id;
|
int m_id;
|
||||||
|
|
||||||
effect *m_shader;
|
effect *m_shader;
|
||||||
@ -142,7 +141,7 @@ class effect
|
|||||||
friend class uniform;
|
friend class uniform;
|
||||||
|
|
||||||
public:
|
public:
|
||||||
effect(shaders *shadersys, device *dev, const char *name, const char *path);
|
effect(shaders *shadersys, IDirect3DDevice9 *dev, const char *name, const char *path);
|
||||||
~effect();
|
~effect();
|
||||||
|
|
||||||
void begin(UINT *passes, DWORD flags);
|
void begin(UINT *passes, DWORD flags);
|
||||||
@ -157,8 +156,8 @@ public:
|
|||||||
void set_float(D3DXHANDLE param, float value);
|
void set_float(D3DXHANDLE param, float value);
|
||||||
void set_int(D3DXHANDLE param, int value);
|
void set_int(D3DXHANDLE param, int value);
|
||||||
void set_bool(D3DXHANDLE param, bool value);
|
void set_bool(D3DXHANDLE param, bool value);
|
||||||
void set_matrix(D3DXHANDLE param, matrix *matrix);
|
void set_matrix(D3DXHANDLE param, D3DMATRIX *matrix);
|
||||||
void set_texture(D3DXHANDLE param, texture *tex);
|
void set_texture(D3DXHANDLE param, IDirect3DTexture9 *tex);
|
||||||
|
|
||||||
void add_uniform(const char *name, uniform::uniform_type type, int id);
|
void add_uniform(const char *name, uniform::uniform_type type, int id);
|
||||||
void update_uniforms();
|
void update_uniforms();
|
||||||
@ -329,8 +328,8 @@ public:
|
|||||||
void window_record();
|
void window_record();
|
||||||
bool recording() const { return avi_output_file != nullptr; }
|
bool recording() const { return avi_output_file != nullptr; }
|
||||||
|
|
||||||
void avi_update_snap(surface *surface);
|
void avi_update_snap(IDirect3DSurface9 *surface);
|
||||||
void render_snapshot(surface *surface);
|
void render_snapshot(IDirect3DSurface9 *surface);
|
||||||
void record_texture();
|
void record_texture();
|
||||||
void init_fsfx_quad(void *vertbuf);
|
void init_fsfx_quad(void *vertbuf);
|
||||||
|
|
||||||
@ -350,7 +349,7 @@ public:
|
|||||||
void *get_slider_option(int id, int index = 0);
|
void *get_slider_option(int id, int index = 0);
|
||||||
|
|
||||||
private:
|
private:
|
||||||
void blit(surface *dst, bool clear_dst, D3DPRIMITIVETYPE prim_type, UINT32 prim_index, UINT32 prim_count);
|
void blit(IDirect3DSurface9 *dst, bool clear_dst, D3DPRIMITIVETYPE prim_type, UINT32 prim_index, UINT32 prim_count);
|
||||||
void enumerate_screens();
|
void enumerate_screens();
|
||||||
|
|
||||||
void end_avi_recording();
|
void end_avi_recording();
|
||||||
@ -399,28 +398,28 @@ private:
|
|||||||
int avi_frame; // AVI frame
|
int avi_frame; // AVI frame
|
||||||
attotime avi_frame_period; // AVI frame period
|
attotime avi_frame_period; // AVI frame period
|
||||||
attotime avi_next_frame_time; // AVI next frame time
|
attotime avi_next_frame_time; // AVI next frame time
|
||||||
surface * avi_copy_surface; // AVI destination surface in system memory
|
IDirect3DSurface9 * avi_copy_surface; // AVI destination surface in system memory
|
||||||
texture * avi_copy_texture; // AVI destination texture in system memory
|
IDirect3DTexture9 * avi_copy_texture; // AVI destination texture in system memory
|
||||||
surface * avi_final_target; // AVI upscaled surface
|
IDirect3DSurface9 * avi_final_target; // AVI upscaled surface
|
||||||
texture * avi_final_texture; // AVI upscaled texture
|
IDirect3DTexture9 * avi_final_texture; // AVI upscaled texture
|
||||||
|
|
||||||
surface * black_surface; // black dummy surface
|
IDirect3DSurface9 * black_surface; // black dummy surface
|
||||||
texture * black_texture; // black dummy texture
|
IDirect3DTexture9 * black_texture; // black dummy texture
|
||||||
|
|
||||||
bool render_snap; // whether or not to take HLSL post-render snapshot
|
bool render_snap; // whether or not to take HLSL post-render snapshot
|
||||||
bool snap_rendered; // whether we just rendered our HLSL post-render shot or not
|
bool snap_rendered; // whether we just rendered our HLSL post-render shot or not
|
||||||
surface * snap_copy_target; // snapshot destination surface in system memory
|
IDirect3DSurface9 * snap_copy_target; // snapshot destination surface in system memory
|
||||||
texture * snap_copy_texture; // snapshot destination surface in system memory
|
IDirect3DTexture9 * snap_copy_texture; // snapshot destination surface in system memory
|
||||||
surface * snap_target; // snapshot upscaled surface
|
IDirect3DSurface9 * snap_target; // snapshot upscaled surface
|
||||||
texture * snap_texture; // snapshot upscaled texture
|
IDirect3DTexture9 * snap_texture; // snapshot upscaled texture
|
||||||
int snap_width; // snapshot width
|
int snap_width; // snapshot width
|
||||||
int snap_height; // snapshot height
|
int snap_height; // snapshot height
|
||||||
bool lines_pending; // whether or not we have lines to flush on the next quad
|
bool lines_pending; // whether or not we have lines to flush on the next quad
|
||||||
|
|
||||||
bool initialized; // whether or not we're initialize
|
bool initialized; // whether or not we're initialized
|
||||||
|
|
||||||
// HLSL effects
|
// HLSL effects
|
||||||
surface * backbuffer; // pointer to our device's backbuffer
|
IDirect3DSurface9 * backbuffer; // pointer to our device's backbuffer
|
||||||
effect * curr_effect; // pointer to the currently active effect object
|
effect * curr_effect; // pointer to the currently active effect object
|
||||||
effect * default_effect; // pointer to the primary-effect object
|
effect * default_effect; // pointer to the primary-effect object
|
||||||
effect * prescale_effect; // pointer to the prescale-effect object
|
effect * prescale_effect; // pointer to the prescale-effect object
|
||||||
@ -447,6 +446,9 @@ private:
|
|||||||
static slider_desc s_sliders[];
|
static slider_desc s_sliders[];
|
||||||
static hlsl_options last_options; // last used options
|
static hlsl_options last_options; // last used options
|
||||||
static char last_system_name[16]; // last used system
|
static char last_system_name[16]; // last used system
|
||||||
|
|
||||||
|
osd::dynamic_module::ptr d3dx9_dll;
|
||||||
|
d3dx_create_effect_from_file_fn d3dx_create_effect_from_file_ptr;
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif
|
#endif
|
||||||
|
File diff suppressed because it is too large
Load Diff
@ -13,8 +13,17 @@
|
|||||||
|
|
||||||
#ifdef OSD_WINDOWS
|
#ifdef OSD_WINDOWS
|
||||||
|
|
||||||
#include "d3d/d3dintf.h"
|
#define WIN32_LEAN_AND_MEAN
|
||||||
|
#include <windows.h>
|
||||||
|
#include <tchar.h>
|
||||||
|
#include <mmsystem.h>
|
||||||
|
#include <d3d9.h>
|
||||||
|
#include <d3dx9.h>
|
||||||
|
#include <math.h>
|
||||||
|
#undef interface
|
||||||
|
|
||||||
#include "d3d/d3dcomm.h"
|
#include "d3d/d3dcomm.h"
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// CONSTANTS
|
// CONSTANTS
|
||||||
@ -27,14 +36,17 @@
|
|||||||
// TYPE DEFINITIONS
|
// TYPE DEFINITIONS
|
||||||
//============================================================
|
//============================================================
|
||||||
|
|
||||||
struct vertex;
|
struct d3d_base
|
||||||
class texture_info;
|
{
|
||||||
class texture_manager;
|
// internal objects
|
||||||
struct device;
|
IDirect3D9 *d3dobj;
|
||||||
struct vertex_buffer;
|
bool post_fx_available;
|
||||||
|
|
||||||
|
osd::dynamic_module::ptr d3d9_dll;
|
||||||
|
};
|
||||||
|
|
||||||
class shaders;
|
class shaders;
|
||||||
struct hlsl_options;
|
struct hlsl_options;
|
||||||
class poly_info;
|
|
||||||
|
|
||||||
/* renderer is the information about Direct3D for the current screen */
|
/* renderer is the information about Direct3D for the current screen */
|
||||||
class renderer_d3d9 : public osd_renderer
|
class renderer_d3d9 : public osd_renderer
|
||||||
@ -97,10 +109,10 @@ public:
|
|||||||
int get_height() const { return m_height; }
|
int get_height() const { return m_height; }
|
||||||
int get_refresh() const { return m_refresh; }
|
int get_refresh() const { return m_refresh; }
|
||||||
|
|
||||||
device * get_device() const { return m_device; }
|
IDirect3DDevice9 * get_device() const { return m_device; }
|
||||||
present_parameters * get_presentation() { return &m_presentation; }
|
D3DPRESENT_PARAMETERS * get_presentation() { return &m_presentation; }
|
||||||
|
|
||||||
vertex_buffer * get_vertex_buffer() const { return m_vertexbuf; }
|
IDirect3DVertexBuffer9 *get_vertex_buffer() const { return m_vertexbuf; }
|
||||||
vertex * get_locked_buffer() const { return m_lockedbuf; }
|
vertex * get_locked_buffer() const { return m_lockedbuf; }
|
||||||
VOID ** get_locked_buffer_ptr()const { return (VOID **)&m_lockedbuf; }
|
VOID ** get_locked_buffer_ptr()const { return (VOID **)&m_lockedbuf; }
|
||||||
void set_locked_buffer(vertex *lockedbuf) { m_lockedbuf = lockedbuf; }
|
void set_locked_buffer(vertex *lockedbuf) { m_lockedbuf = lockedbuf; }
|
||||||
@ -128,13 +140,13 @@ private:
|
|||||||
int m_refresh; // current refresh rate
|
int m_refresh; // current refresh rate
|
||||||
int m_create_error_count; // number of consecutive create errors
|
int m_create_error_count; // number of consecutive create errors
|
||||||
|
|
||||||
device * m_device; // pointer to the Direct3DDevice object
|
IDirect3DDevice9 * m_device; // pointer to the Direct3DDevice object
|
||||||
int m_gamma_supported; // is full screen gamma supported?
|
int m_gamma_supported; // is full screen gamma supported?
|
||||||
present_parameters m_presentation; // set of presentation parameters
|
D3DPRESENT_PARAMETERS m_presentation; // set of presentation parameters
|
||||||
D3DDISPLAYMODE m_origmode; // original display mode for the adapter
|
D3DDISPLAYMODE m_origmode; // original display mode for the adapter
|
||||||
D3DFORMAT m_pixformat; // pixel format we are using
|
D3DFORMAT m_pixformat; // pixel format we are using
|
||||||
|
|
||||||
vertex_buffer * m_vertexbuf; // pointer to the vertex buffer object
|
IDirect3DVertexBuffer9 *m_vertexbuf; // pointer to the vertex buffer object
|
||||||
vertex * m_lockedbuf; // pointer to the locked vertex buffer
|
vertex * m_lockedbuf; // pointer to the locked vertex buffer
|
||||||
int m_numverts; // number of accumulated vertices
|
int m_numverts; // number of accumulated vertices
|
||||||
|
|
||||||
|
@ -360,17 +360,11 @@ static void loadgl_functions(osd_gl_context *context)
|
|||||||
osd_gl_dispatch *gl_dispatch;
|
osd_gl_dispatch *gl_dispatch;
|
||||||
#endif
|
#endif
|
||||||
|
|
||||||
#ifdef OSD_WINDOWS
|
|
||||||
HMODULE win_gl_context::m_module;
|
|
||||||
#endif
|
|
||||||
|
|
||||||
void renderer_ogl::load_gl_lib(running_machine &machine)
|
void renderer_ogl::load_gl_lib(running_machine &machine)
|
||||||
{
|
{
|
||||||
if (!s_dll_loaded)
|
if (!s_dll_loaded)
|
||||||
{
|
{
|
||||||
#ifdef OSD_WINDOWS
|
#ifndef OSD_WINDOWS
|
||||||
win_gl_context::load_library();
|
|
||||||
#else
|
|
||||||
#ifdef USE_DISPATCH_GL
|
#ifdef USE_DISPATCH_GL
|
||||||
/*
|
/*
|
||||||
* directfb and and x11 use this env var
|
* directfb and and x11 use this env var
|
||||||
|
@ -14,6 +14,17 @@
|
|||||||
#define __WIN_GL_CONTEXT__
|
#define __WIN_GL_CONTEXT__
|
||||||
|
|
||||||
#include "modules/opengl/osd_opengl.h"
|
#include "modules/opengl/osd_opengl.h"
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
|
// Typedefs for dynamically loaded functions
|
||||||
|
typedef PROC WINAPI (*wglGetProcAddress_fn)(LPCSTR);
|
||||||
|
typedef HGLRC WINAPI (*wglCreateContext_fn)(HDC);
|
||||||
|
typedef BOOL WINAPI (*wglDeleteContext_fn)(HGLRC);
|
||||||
|
typedef BOOL WINAPI (*wglMakeCurrent_fn)(HDC, HGLRC);
|
||||||
|
|
||||||
|
typedef const char * WINAPI (*wglGetExtensionsStringEXT_fn)(void);
|
||||||
|
typedef BOOL WINAPI (*wglSwapIntervalEXT_fn)(int);
|
||||||
|
typedef int WINAPI (*wglGetSwapIntervalEXT_fn)(void);
|
||||||
|
|
||||||
class win_gl_context : public osd_gl_context
|
class win_gl_context : public osd_gl_context
|
||||||
{
|
{
|
||||||
@ -22,17 +33,25 @@ public:
|
|||||||
{
|
{
|
||||||
m_error[0] = 0;
|
m_error[0] = 0;
|
||||||
|
|
||||||
this->pfn_wglGetProcAddress = (PROC (WINAPI *)(LPCSTR lpszProc)) GetProcAddress(m_module, "wglGetProcAddress");
|
opengl32_dll = osd::dynamic_module::open({ "opengl32.dll" });
|
||||||
this->pfn_wglCreateContext = (HGLRC (WINAPI *)(HDC hdc)) GetProcAddress(m_module, "wglCreateContext");
|
|
||||||
this->pfn_wglDeleteContext = (BOOL (WINAPI *)(HGLRC hglrc)) GetProcAddress(m_module, "wglDeleteContext");
|
|
||||||
this->pfn_wglMakeCurrent = (BOOL (WINAPI *)(HDC hdc, HGLRC hglrc)) GetProcAddress(m_module, "wglMakeCurrent");
|
|
||||||
|
|
||||||
this->pfn_wglGetExtensionsStringEXT = (const char *(WINAPI *) (void)) pfn_wglGetProcAddress("wglGetExtensionsStringEXT");
|
pfn_wglGetProcAddress = opengl32_dll->bind<wglGetProcAddress_fn>("wglGetProcAddress");
|
||||||
|
pfn_wglCreateContext = opengl32_dll->bind<wglCreateContext_fn>("wglCreateContext");
|
||||||
|
pfn_wglDeleteContext = opengl32_dll->bind<wglDeleteContext_fn>("wglDeleteContext");
|
||||||
|
pfn_wglMakeCurrent = opengl32_dll->bind<wglMakeCurrent_fn>("wglMakeCurrent");
|
||||||
|
|
||||||
|
if (pfn_wglGetProcAddress == nullptr || pfn_wglCreateContext == nullptr ||
|
||||||
|
pfn_wglDeleteContext == nullptr || pfn_wglMakeCurrent == nullptr)
|
||||||
|
{
|
||||||
|
return;
|
||||||
|
}
|
||||||
|
|
||||||
|
pfn_wglGetExtensionsStringEXT = (wglGetExtensionsStringEXT_fn)(*pfn_wglGetProcAddress)("wglGetExtensionsStringEXT");
|
||||||
|
|
||||||
if (WGLExtensionSupported("WGL_EXT_swap_control"))
|
if (WGLExtensionSupported("WGL_EXT_swap_control"))
|
||||||
{
|
{
|
||||||
this->pfn_wglSwapIntervalEXT = (BOOL (WINAPI *) (int)) getProcAddress("wglSwapIntervalEXT");
|
pfn_wglSwapIntervalEXT = (BOOL (WINAPI *) (int)) getProcAddress("wglSwapIntervalEXT");
|
||||||
this->pfn_wglGetSwapIntervalEXT = (int (WINAPI *) (void)) getProcAddress("wglGetSwapIntervalEXT");
|
pfn_wglGetSwapIntervalEXT = (int (WINAPI *) (void)) getProcAddress("wglGetSwapIntervalEXT");
|
||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
@ -43,25 +62,25 @@ public:
|
|||||||
m_hdc = GetDC(window);
|
m_hdc = GetDC(window);
|
||||||
if (!setupPixelFormat(m_hdc))
|
if (!setupPixelFormat(m_hdc))
|
||||||
{
|
{
|
||||||
m_context = this->pfn_wglCreateContext(m_hdc);
|
m_context = (*pfn_wglCreateContext)(m_hdc);
|
||||||
if (!m_context)
|
if (!m_context)
|
||||||
{
|
{
|
||||||
FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, nullptr, GetLastError(), 0, m_error, 255, nullptr);
|
FormatMessageA(FORMAT_MESSAGE_FROM_SYSTEM | FORMAT_MESSAGE_IGNORE_INSERTS, nullptr, GetLastError(), 0, m_error, 255, nullptr);
|
||||||
return;
|
return;
|
||||||
}
|
}
|
||||||
this->pfn_wglMakeCurrent(m_hdc, m_context);
|
(*pfn_wglMakeCurrent)(m_hdc, m_context);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual ~win_gl_context()
|
virtual ~win_gl_context()
|
||||||
{
|
{
|
||||||
this->pfn_wglDeleteContext(m_context);
|
(*pfn_wglDeleteContext)(m_context);
|
||||||
ReleaseDC(m_window, m_hdc);
|
ReleaseDC(m_window, m_hdc);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual void MakeCurrent() override
|
virtual void MakeCurrent() override
|
||||||
{
|
{
|
||||||
this->pfn_wglMakeCurrent(m_hdc, m_context);
|
(*pfn_wglMakeCurrent)(m_hdc, m_context);
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual const char *LastErrorMsg() override
|
virtual const char *LastErrorMsg() override
|
||||||
@ -74,17 +93,14 @@ public:
|
|||||||
|
|
||||||
virtual void *getProcAddress(const char *proc) override
|
virtual void *getProcAddress(const char *proc) override
|
||||||
{
|
{
|
||||||
void *ret = (void *) GetProcAddress(m_module, proc);
|
return (void *)(*pfn_wglGetProcAddress)(proc);
|
||||||
if (ret == nullptr)
|
|
||||||
ret = (void *) this->pfn_wglGetProcAddress(proc);
|
|
||||||
return ret;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
virtual int SetSwapInterval(const int swap) override
|
virtual int SetSwapInterval(const int swap) override
|
||||||
{
|
{
|
||||||
if (this->pfn_wglSwapIntervalEXT != nullptr)
|
if (pfn_wglSwapIntervalEXT != nullptr)
|
||||||
{
|
{
|
||||||
this->pfn_wglSwapIntervalEXT(swap ? 1 : 0);
|
pfn_wglSwapIntervalEXT(swap ? 1 : 0);
|
||||||
}
|
}
|
||||||
return 0;
|
return 0;
|
||||||
}
|
}
|
||||||
@ -95,11 +111,6 @@ public:
|
|||||||
//wglSwapLayerBuffers(GetDC(window().m_hwnd), WGL_SWAP_MAIN_PLANE);
|
//wglSwapLayerBuffers(GetDC(window().m_hwnd), WGL_SWAP_MAIN_PLANE);
|
||||||
}
|
}
|
||||||
|
|
||||||
static void load_library()
|
|
||||||
{
|
|
||||||
m_module = LoadLibraryA("opengl32.dll");
|
|
||||||
}
|
|
||||||
|
|
||||||
private:
|
private:
|
||||||
|
|
||||||
int setupPixelFormat(HDC hDC)
|
int setupPixelFormat(HDC hDC)
|
||||||
@ -124,15 +135,17 @@ private:
|
|||||||
0, /* reserved */
|
0, /* reserved */
|
||||||
0, 0, 0, /* no layer, visible, damage masks */
|
0, 0, 0, /* no layer, visible, damage masks */
|
||||||
};
|
};
|
||||||
int pixelFormat;
|
|
||||||
|
|
||||||
pixelFormat = ChoosePixelFormat(hDC, &pfd);
|
int pixelFormat = ChoosePixelFormat(hDC, &pfd);
|
||||||
if (pixelFormat == 0) {
|
|
||||||
strcpy(m_error, "ChoosePixelFormat failed");
|
if (pixelFormat == 0)
|
||||||
|
{
|
||||||
|
strcpy(m_error, "ChoosePixelFormat failed.");
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (SetPixelFormat(hDC, pixelFormat, &pfd) != TRUE) {
|
if (SetPixelFormat(hDC, pixelFormat, &pfd) != TRUE)
|
||||||
|
{
|
||||||
strcpy(m_error, "SetPixelFormat failed.");
|
strcpy(m_error, "SetPixelFormat failed.");
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
@ -141,10 +154,12 @@ private:
|
|||||||
|
|
||||||
bool WGLExtensionSupported(const char *extension_name)
|
bool WGLExtensionSupported(const char *extension_name)
|
||||||
{
|
{
|
||||||
//if (pfn_wglGetExtensionsStringEXT != nullptr)
|
if (pfn_wglGetExtensionsStringEXT == nullptr)
|
||||||
// printf("%s\n", this->pfn_wglGetExtensionsStringEXT());
|
return false;
|
||||||
|
|
||||||
|
// printf("%s\n", pfn_wglGetExtensionsStringEXT());
|
||||||
|
|
||||||
if (pfn_wglGetExtensionsStringEXT != nullptr && strstr(pfn_wglGetExtensionsStringEXT(), extension_name) != nullptr)
|
if (strstr(pfn_wglGetExtensionsStringEXT(), extension_name) != nullptr)
|
||||||
return true;
|
return true;
|
||||||
else
|
else
|
||||||
return false;
|
return false;
|
||||||
@ -155,16 +170,15 @@ private:
|
|||||||
HDC m_hdc;
|
HDC m_hdc;
|
||||||
char m_error[256];
|
char m_error[256];
|
||||||
|
|
||||||
PROC (WINAPI *pfn_wglGetProcAddress)(LPCSTR lpszProc);
|
osd::dynamic_module::ptr opengl32_dll;
|
||||||
HGLRC (WINAPI *pfn_wglCreateContext)(HDC hdc);
|
wglGetProcAddress_fn pfn_wglGetProcAddress;
|
||||||
BOOL (WINAPI *pfn_wglDeleteContext)(HGLRC hglrc);
|
wglCreateContext_fn pfn_wglCreateContext;
|
||||||
BOOL (WINAPI *pfn_wglMakeCurrent)(HDC hdc, HGLRC hglrc);
|
wglDeleteContext_fn pfn_wglDeleteContext;
|
||||||
|
wglMakeCurrent_fn pfn_wglMakeCurrent;
|
||||||
|
|
||||||
const char *(WINAPI *pfn_wglGetExtensionsStringEXT) (void);
|
wglGetExtensionsStringEXT_fn pfn_wglGetExtensionsStringEXT;
|
||||||
BOOL (WINAPI *pfn_wglSwapIntervalEXT) (int interval);
|
wglSwapIntervalEXT_fn pfn_wglSwapIntervalEXT;
|
||||||
int (WINAPI * pfn_wglGetSwapIntervalEXT) (void);
|
wglGetSwapIntervalEXT_fn pfn_wglGetSwapIntervalEXT;
|
||||||
|
|
||||||
static HMODULE m_module;
|
|
||||||
};
|
};
|
||||||
|
|
||||||
#endif // __WIN_GL_CONTEXT__
|
#endif // __WIN_GL_CONTEXT__
|
||||||
|
62
src/osd/modules/sound/xaudio2_sound.cpp
Normal file → Executable file
62
src/osd/modules/sound/xaudio2_sound.cpp
Normal file → Executable file
@ -33,6 +33,8 @@
|
|||||||
|
|
||||||
#include "winutil.h"
|
#include "winutil.h"
|
||||||
|
|
||||||
|
#include "modules/lib/osdlib.h"
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// Constants
|
// Constants
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -118,7 +120,7 @@ typedef std::unique_ptr<IXAudio2MasteringVoice, xaudio2_custom_deleter> masterin
|
|||||||
typedef std::unique_ptr<IXAudio2SourceVoice, xaudio2_custom_deleter> src_voice_ptr;
|
typedef std::unique_ptr<IXAudio2SourceVoice, xaudio2_custom_deleter> src_voice_ptr;
|
||||||
|
|
||||||
// Typedef for pointer to XAudio2Create
|
// Typedef for pointer to XAudio2Create
|
||||||
typedef lazy_loaded_function_p3<HRESULT, IXAudio2**, UINT32, XAUDIO2_PROCESSOR> xaudio2_create_ptr;
|
typedef HRESULT (*xaudio2_create_ptr)(IXAudio2 **, UINT32, XAUDIO2_PROCESSOR);
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
// Helper classes
|
// Helper classes
|
||||||
@ -181,28 +183,27 @@ public:
|
|||||||
class sound_xaudio2 : public osd_module, public sound_module, public IXAudio2VoiceCallback
|
class sound_xaudio2 : public osd_module, public sound_module, public IXAudio2VoiceCallback
|
||||||
{
|
{
|
||||||
private:
|
private:
|
||||||
const wchar_t* XAUDIO_DLLS[2] = { L"XAudio2_9.dll", L"XAudio2_8.dll" };
|
Microsoft::WRL::ComPtr<IXAudio2> m_xAudio2;
|
||||||
|
mastering_voice_ptr m_masterVoice;
|
||||||
Microsoft::WRL::ComPtr<IXAudio2> m_xAudio2;
|
src_voice_ptr m_sourceVoice;
|
||||||
mastering_voice_ptr m_masterVoice;
|
DWORD m_sample_bytes;
|
||||||
src_voice_ptr m_sourceVoice;
|
std::unique_ptr<BYTE[]> m_buffer;
|
||||||
DWORD m_sample_bytes;
|
DWORD m_buffer_size;
|
||||||
std::unique_ptr<BYTE[]> m_buffer;
|
DWORD m_buffer_count;
|
||||||
DWORD m_buffer_size;
|
DWORD m_writepos;
|
||||||
DWORD m_buffer_count;
|
std::mutex m_buffer_lock;
|
||||||
DWORD m_writepos;
|
HANDLE m_hEventBufferCompleted;
|
||||||
std::mutex m_buffer_lock;
|
HANDLE m_hEventDataAvailable;
|
||||||
HANDLE m_hEventBufferCompleted;
|
HANDLE m_hEventExiting;
|
||||||
HANDLE m_hEventDataAvailable;
|
std::thread m_audioThread;
|
||||||
HANDLE m_hEventExiting;
|
std::queue<xaudio2_buffer> m_queue;
|
||||||
std::thread m_audioThread;
|
std::unique_ptr<bufferpool> m_buffer_pool;
|
||||||
std::queue<xaudio2_buffer> m_queue;
|
UINT32 m_overflows;
|
||||||
std::unique_ptr<bufferpool> m_buffer_pool;
|
UINT32 m_underflows;
|
||||||
UINT32 m_overflows;
|
BOOL m_in_underflow;
|
||||||
UINT32 m_underflows;
|
osd::dynamic_module::ptr m_xaudio_dll;
|
||||||
BOOL m_in_underflow;
|
xaudio2_create_ptr XAudio2Create;
|
||||||
xaudio2_create_ptr XAudio2Create;
|
BOOL m_initialized;
|
||||||
BOOL m_initialized;
|
|
||||||
|
|
||||||
public:
|
public:
|
||||||
sound_xaudio2() :
|
sound_xaudio2() :
|
||||||
@ -223,7 +224,6 @@ public:
|
|||||||
m_overflows(0),
|
m_overflows(0),
|
||||||
m_underflows(0),
|
m_underflows(0),
|
||||||
m_in_underflow(FALSE),
|
m_in_underflow(FALSE),
|
||||||
XAudio2Create("XAudio2Create", XAUDIO_DLLS, ARRAY_LENGTH(XAUDIO_DLLS)),
|
|
||||||
m_initialized(FALSE)
|
m_initialized(FALSE)
|
||||||
{
|
{
|
||||||
}
|
}
|
||||||
@ -261,8 +261,13 @@ private:
|
|||||||
|
|
||||||
bool sound_xaudio2::probe()
|
bool sound_xaudio2::probe()
|
||||||
{
|
{
|
||||||
int status = XAudio2Create.initialize();
|
m_xaudio_dll = osd::dynamic_module::open({ "XAudio2_9.dll", "XAudio2_8.dll" });
|
||||||
return status == 0;
|
if (m_xaudio_dll == nullptr)
|
||||||
|
return false;
|
||||||
|
|
||||||
|
XAudio2Create = m_xaudio_dll->bind<xaudio2_create_ptr>("XAudio2Create");
|
||||||
|
|
||||||
|
return (XAudio2Create ? true : false);
|
||||||
}
|
}
|
||||||
|
|
||||||
//============================================================
|
//============================================================
|
||||||
@ -276,10 +281,9 @@ int sound_xaudio2::init(osd_options const &options)
|
|||||||
CoInitializeEx(nullptr, COINIT_MULTITHREADED);
|
CoInitializeEx(nullptr, COINIT_MULTITHREADED);
|
||||||
|
|
||||||
// Make sure our XAudio2Create entrypoint is bound
|
// Make sure our XAudio2Create entrypoint is bound
|
||||||
int status = XAudio2Create.initialize();
|
if (!XAudio2Create)
|
||||||
if (status != 0)
|
|
||||||
{
|
{
|
||||||
osd_printf_error("Could not find XAudio2 library\n");
|
osd_printf_error("Could not find XAudio2. Please try to reinstall DirectX runtime package.\n");
|
||||||
return 1;
|
return 1;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -111,67 +111,3 @@ HMODULE WINAPI GetModuleHandleUni()
|
|||||||
VirtualQuery((LPCVOID)GetModuleHandleUni, &mbi, sizeof(mbi));
|
VirtualQuery((LPCVOID)GetModuleHandleUni, &mbi, sizeof(mbi));
|
||||||
return (HMODULE)mbi.AllocationBase;
|
return (HMODULE)mbi.AllocationBase;
|
||||||
}
|
}
|
||||||
|
|
||||||
//-----------------------------------------------------------
|
|
||||||
// Lazy loaded function using LoadLibrary / GetProcAddress
|
|
||||||
//-----------------------------------------------------------
|
|
||||||
|
|
||||||
lazy_loaded_function::lazy_loaded_function(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function::lazy_loaded_function(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: m_name(name), m_module(nullptr), m_initialized(false), m_pfn(nullptr)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < dll_count; i++)
|
|
||||||
m_dll_names.push_back(std::wstring(dll_names[i]));
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function::~lazy_loaded_function()
|
|
||||||
{
|
|
||||||
if (m_module != nullptr)
|
|
||||||
{
|
|
||||||
FreeLibrary(m_module);
|
|
||||||
m_module = nullptr;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
int lazy_loaded_function::initialize()
|
|
||||||
{
|
|
||||||
if (m_module == nullptr)
|
|
||||||
{
|
|
||||||
for (int i = 0; i < m_dll_names.size(); i++)
|
|
||||||
{
|
|
||||||
m_module = LoadLibraryW(m_dll_names[i].c_str());
|
|
||||||
if (m_module != nullptr)
|
|
||||||
break;
|
|
||||||
}
|
|
||||||
|
|
||||||
if (m_module == nullptr)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Could not find DLL to dynamically link function %s.\n", m_name.c_str());
|
|
||||||
return ERROR_DLL_NOT_FOUND;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
if (m_pfn == nullptr)
|
|
||||||
{
|
|
||||||
m_pfn = GetProcAddress(m_module, m_name.c_str());
|
|
||||||
if (m_pfn == nullptr)
|
|
||||||
{
|
|
||||||
osd_printf_verbose("Could not find function address to dynamically link function %s.\n", m_name.c_str());
|
|
||||||
return ERROR_NOT_FOUND;
|
|
||||||
}
|
|
||||||
}
|
|
||||||
|
|
||||||
m_initialized = true;
|
|
||||||
|
|
||||||
return 0;
|
|
||||||
}
|
|
||||||
|
|
||||||
void lazy_loaded_function::check_init() const
|
|
||||||
{
|
|
||||||
if (!m_initialized)
|
|
||||||
fatalerror("Attempt to use function pointer for function %s prior to init!", name());
|
|
||||||
}
|
|
||||||
|
@ -18,160 +18,4 @@ osd_dir_entry_type win_attributes_to_entry_type(DWORD attributes);
|
|||||||
BOOL win_is_gui_application(void);
|
BOOL win_is_gui_application(void);
|
||||||
HMODULE WINAPI GetModuleHandleUni();
|
HMODULE WINAPI GetModuleHandleUni();
|
||||||
|
|
||||||
//-----------------------------------------------------------
|
|
||||||
// Lazy loaded function using LoadLibrary / GetProcAddress
|
|
||||||
//-----------------------------------------------------------
|
|
||||||
|
|
||||||
class lazy_loaded_function
|
|
||||||
{
|
|
||||||
private:
|
|
||||||
std::string m_name;
|
|
||||||
std::vector<std::wstring> m_dll_names;
|
|
||||||
HMODULE m_module;
|
|
||||||
bool m_initialized;
|
|
||||||
|
|
||||||
protected:
|
|
||||||
void check_init() const;
|
|
||||||
FARPROC m_pfn;
|
|
||||||
|
|
||||||
public:
|
|
||||||
lazy_loaded_function(const char * name, const wchar_t* dll_name);
|
|
||||||
lazy_loaded_function(const char * name, const wchar_t** dll_names, int dll_count);
|
|
||||||
~lazy_loaded_function();
|
|
||||||
int initialize();
|
|
||||||
const char * name() const { return m_name.c_str(); }
|
|
||||||
};
|
|
||||||
|
|
||||||
// No parameters
|
|
||||||
template <class TRet>
|
|
||||||
class lazy_loaded_function_ret : public lazy_loaded_function
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
lazy_loaded_function_ret(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function_ret(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: lazy_loaded_function(name, dll_names, dll_count)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
TRet operator ()()
|
|
||||||
{
|
|
||||||
check_init();
|
|
||||||
return ((TRet(__stdcall *) ())m_pfn)();
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// One parameter
|
|
||||||
template <class TRet, class P1>
|
|
||||||
class lazy_loaded_function_p1 : public lazy_loaded_function
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
lazy_loaded_function_p1(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function_p1(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: lazy_loaded_function(name, dll_names, dll_count)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
TRet operator ()(P1 p1)
|
|
||||||
{
|
|
||||||
check_init();
|
|
||||||
return ((TRet(__stdcall *) (P1))m_pfn)(p1);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// Two parameters
|
|
||||||
template <class TRet, class P1, class P2>
|
|
||||||
class lazy_loaded_function_p2 : public lazy_loaded_function
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
lazy_loaded_function_p2(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function_p2(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: lazy_loaded_function(name, dll_names, dll_count)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
TRet operator ()(P1 p1, P2 p2)
|
|
||||||
{
|
|
||||||
check_init();
|
|
||||||
return ((TRet(__stdcall *) (P1, P2))m_pfn)(p1, p2);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// Three parameters
|
|
||||||
template <class TRet, class P1, class P2, class P3>
|
|
||||||
class lazy_loaded_function_p3 : public lazy_loaded_function
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
lazy_loaded_function_p3(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function_p3(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: lazy_loaded_function(name, dll_names, dll_count)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
TRet operator ()(P1 p1, P2 p2, P3 p3)
|
|
||||||
{
|
|
||||||
check_init();
|
|
||||||
return ((TRet(__stdcall *) (P1, P2, P3))m_pfn)(p1, p2, p3);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// Four parameters
|
|
||||||
template <class TRet, class P1, class P2, class P3, class P4>
|
|
||||||
class lazy_loaded_function_p4 : public lazy_loaded_function
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
lazy_loaded_function_p4(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function_p4(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: lazy_loaded_function(name, dll_names, dll_count)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
TRet operator ()(P1 p1, P2 p2, P3 p3, P4 p4)
|
|
||||||
{
|
|
||||||
check_init();
|
|
||||||
return ((TRet(__stdcall *) (P1, P2, P3, P4))m_pfn)(p1, p2, p3, p4);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
// Five parameters
|
|
||||||
template <class TRet, class P1, class P2, class P3, class P4, class P5>
|
|
||||||
class lazy_loaded_function_p5 : public lazy_loaded_function
|
|
||||||
{
|
|
||||||
public:
|
|
||||||
lazy_loaded_function_p5(const char * name, const wchar_t* dll_name)
|
|
||||||
: lazy_loaded_function(name, &dll_name, 1)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
lazy_loaded_function_p5(const char * name, const wchar_t** dll_names, int dll_count)
|
|
||||||
: lazy_loaded_function(name, dll_names, dll_count)
|
|
||||||
{
|
|
||||||
}
|
|
||||||
|
|
||||||
TRet operator ()(P1 p1, P2 p2, P3 p3, P4 p4, P5 p5)
|
|
||||||
{
|
|
||||||
check_init();
|
|
||||||
return ((TRet(__stdcall *) (P1, P2, P3, P4, P5))m_pfn)(p1, p2, p3, p4, p5);
|
|
||||||
}
|
|
||||||
};
|
|
||||||
|
|
||||||
#endif // __WINUTIL__
|
#endif // __WINUTIL__
|
||||||
|
Loading…
Reference in New Issue
Block a user