Skip to content

Commit

Permalink
Ensuring thread safety on Client to Server interactions for APIs that…
Browse files Browse the repository at this point in the history
… are not D3D9 Device dependent
  • Loading branch information
lvengesanam committed Jun 9, 2023
1 parent a18db5f commit bb48ac3
Show file tree
Hide file tree
Showing 3 changed files with 27 additions and 3 deletions.
24 changes: 23 additions & 1 deletion src/client/d3d9_module.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -28,6 +28,9 @@
#include "util_bridge_assert.h"
#include "util_modulecommand.h"

#define BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD \
BRIDGE_COMMAND_LOCKGUARD(ModuleBridge::getWriterChannel().m_mutex) \

#undef WAIT_FOR_SERVER_RESPONSE
#define WAIT_FOR_SERVER_RESPONSE(func, value) \
{ \
Expand Down Expand Up @@ -87,7 +90,10 @@ void Direct3D9Ex_LSS::onDestroy() {
Logger::warn("Command queue was not flushed at Direct3D module eviction.");
}

ModuleClientCommand { Commands::IDirect3D9Ex_Destroy, getId() };
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand { Commands::IDirect3D9Ex_Destroy, getId() };
}

// Make sure server consumed IDirect3D9Ex_Destroy
ModuleBridge::ensureQueueEmpty();
Expand All @@ -108,6 +114,7 @@ UINT Direct3D9Ex_LSS::GetAdapterCount() {

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterCount);
}
WAIT_FOR_SERVER_RESPONSE("GetAdapterCount()", 0);
Expand Down Expand Up @@ -136,6 +143,7 @@ HRESULT Direct3D9Ex_LSS::GetAdapterIdentifier(UINT Adapter, DWORD Flags, D3DADAP

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterIdentifier);
c.send_many(Adapter, Flags);
}
Expand Down Expand Up @@ -170,6 +178,7 @@ UINT Direct3D9Ex_LSS::GetAdapterModeCount(UINT Adapter, D3DFORMAT Format) {

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterModeCount);
c.send_many(Adapter, Format);
}
Expand All @@ -195,6 +204,7 @@ HRESULT Direct3D9Ex_LSS::EnumAdapterModes(UINT Adapter, D3DFORMAT Format, UINT M

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_EnumAdapterModes);
c.send_many(Adapter, Format, Mode);
}
Expand Down Expand Up @@ -228,6 +238,7 @@ HRESULT Direct3D9Ex_LSS::GetAdapterDisplayMode(UINT Adapter, D3DDISPLAYMODE* pMo

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterDisplayMode);
c.send_data(Adapter);
}
Expand Down Expand Up @@ -256,6 +267,7 @@ HRESULT Direct3D9Ex_LSS::CheckDeviceType(UINT Adapter, D3DDEVTYPE CheckType, D3D

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_CheckDeviceType);
c.send_many(Adapter, CheckType, DisplayFormat, BackBufferFormat, Windowed);
}
Expand All @@ -275,6 +287,7 @@ HRESULT Direct3D9Ex_LSS::CheckDeviceFormat(UINT Adapter, D3DDEVTYPE DeviceType,

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_CheckDeviceFormat);
c.send_many(Adapter, DeviceType, AdapterFormat, Usage, RType, CheckFormat);
}
Expand All @@ -298,6 +311,7 @@ HRESULT Direct3D9Ex_LSS::CheckDeviceMultiSampleType(UINT Adapter, D3DDEVTYPE Dev

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_CheckDeviceMultiSampleType);
c.send_many(Adapter, DeviceType, SurfaceFormat, Windowed, MultiSampleType);
}
Expand All @@ -323,6 +337,7 @@ HRESULT Direct3D9Ex_LSS::CheckDepthStencilMatch(UINT Adapter, D3DDEVTYPE DeviceT

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_CheckDepthStencilMatch);
c.send_many(Adapter, DeviceType, AdapterFormat, RenderTargetFormat, DepthStencilFormat);
}
Expand All @@ -342,6 +357,7 @@ HRESULT Direct3D9Ex_LSS::CheckDeviceFormatConversion(UINT Adapter, D3DDEVTYPE De

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_CheckDeviceFormatConversion);
c.send_many(Adapter, DeviceType, SourceFormat, TargetFormat);
}
Expand Down Expand Up @@ -370,6 +386,7 @@ HRESULT Direct3D9Ex_LSS::GetDeviceCaps(UINT Adapter, D3DDEVTYPE DeviceType, D3DC

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetDeviceCaps);
c.send_many(Adapter, DeviceType);
}
Expand All @@ -394,6 +411,7 @@ HMONITOR Direct3D9Ex_LSS::GetAdapterMonitor(UINT Adapter) {

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterMonitor);
c.send_data(Adapter);
}
Expand Down Expand Up @@ -430,6 +448,7 @@ UINT Direct3D9Ex_LSS::GetAdapterModeCountEx(UINT Adapter, CONST D3DDISPLAYMODEFI
UINT cnt = 0;
// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterModeCountEx, getId());
c.send_data(Adapter);
c.send_data(sizeof(D3DDISPLAYMODEFILTER), pFilter);
Expand All @@ -455,6 +474,7 @@ HRESULT Direct3D9Ex_LSS::EnumAdapterModesEx(UINT Adapter, CONST D3DDISPLAYMODEFI

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_EnumAdapterModesEx);
c.send_data(Adapter);
c.send_data(Mode);
Expand Down Expand Up @@ -488,6 +508,7 @@ HRESULT Direct3D9Ex_LSS::GetAdapterDisplayModeEx(UINT Adapter, D3DDISPLAYMODEEX*

// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterDisplayModeEx);
c.send_data(Adapter);
c.send_data(sizeof(D3DDISPLAYMODEEX), pMode);
Expand Down Expand Up @@ -540,6 +561,7 @@ HRESULT Direct3D9Ex_LSS::GetAdapterLUID(UINT Adapter, LUID* pLUID) {
}
// Send command to server and wait for response
{
BRIDGE_MODULE_WRITE_COMMAND_LOCKGUARD;
ModuleClientCommand c(Commands::IDirect3D9Ex_GetAdapterLUID);
c.send_data(Adapter);
}
Expand Down
5 changes: 3 additions & 2 deletions src/util/util_bridgecommand.h
Original file line number Diff line number Diff line change
Expand Up @@ -34,6 +34,9 @@

extern bool gbBridgeRunning;

#define BRIDGE_COMMAND_LOCKGUARD(currentMutex) \
std::scoped_lock lockObj(currentMutex); \

#define WAIT_FOR_SERVER_RESPONSE(func, value) \
{ \
const uint32_t timeoutMs = GlobalOptions::getAckTimeout(); \
Expand Down Expand Up @@ -289,12 +292,10 @@ class Bridge {
Bridge() = delete;
Bridge(const Bridge&) = delete;
Bridge(const Bridge&&) = delete;

static inline WriterChannel* s_pWriterChannel = nullptr;
static inline ReaderChannel* s_pReaderChannel = nullptr;
static inline int32_t s_curBatchStartPos = -1;
static inline size_t s_cmdCounter = 0;

#if defined(REMIX_BRIDGE_CLIENT)
static constexpr char kWriterChannelName[] = "Client2Server";
static constexpr char kReaderChannelName[] = "Server2Client";
Expand Down
1 change: 1 addition & 0 deletions src/util/util_ipcchannel.h
Original file line number Diff line number Diff line change
Expand Up @@ -100,6 +100,7 @@ class IpcChannel {
bridge_util::DataQueue* const data;
bridge_util::NamedSemaphore* const dataSemaphore;
std::atomic<bool>* const pbCmdInProgress;
mutable std::mutex m_mutex;
};
using WriterChannel = IpcChannel<bridge_util::Accessor::Writer>;
using ReaderChannel = IpcChannel<bridge_util::Accessor::Reader>;

0 comments on commit bb48ac3

Please sign in to comment.