1010 *****************************************************************************/
1111
1212#include " StdInc.h"
13+ #include " CProxyComHelpers.h"
1314#include " ComPtrValidation.h"
1415#include < dwmapi.h>
16+ #include < mutex>
17+ #include < atomic>
1518#include < resource.h>
1619
1720extern HINSTANCE g_hModule;
1821
1922namespace
2023{
21- template <typename T>
22- void ReleaseInterface (T*& pointer, const char * context = nullptr )
23- {
24- if (!pointer)
25- return ;
26-
27- T* heldPointer = pointer;
28-
29- const bool valid = IsValidComInterfacePointer (pointer, ComPtrValidation::ValidationMode::ForceRefresh);
30-
31- if (valid)
32- {
33- heldPointer->Release ();
34- }
35- else
36- {
37- SString label;
38- label = context ? context : " ReleaseInterface" ;
39- SString message;
40- message.Format (" %s: skipping Release on invalid COM pointer %p" , label.c_str (), heldPointer);
41- AddReportLog (8752 , message, 5 );
42- ComPtrValidation::Invalidate (heldPointer);
43- }
44-
45- pointer = nullptr ;
46- }
47-
48- template <typename T>
49- void ReplaceInterface (T*& destination, T* source, const char * context = nullptr )
50- {
51- if (destination == source)
52- return ;
53-
54- if (source && !IsValidComInterfacePointer (source, ComPtrValidation::ValidationMode::ForceRefresh))
55- {
56- SString label;
57- label = context ? context : " ReplaceInterface" ;
58- SString message;
59- message.Format (" %s: rejected invalid COM pointer %p" , label.c_str (), source);
60- AddReportLog (8753 , message, 5 );
61- return ;
62- }
63-
64- ReleaseInterface (destination, context);
65- destination = source;
66- if (destination)
67- destination->AddRef ();
68- }
6924
7025IDirect3D9* GetFirstValidTrackedDirect3D (std::vector<IDirect3D9*>& trackedList)
7126{
@@ -88,7 +43,9 @@ IDirect3D9* GetFirstValidTrackedDirect3D(std::vector<IDirect3D9*>& trackedList)
8843
8944HRESULT HandleCreateDeviceResult (HRESULT hResult, IDirect3D9* pDirect3D, UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags,
9045 D3DPRESENT_PARAMETERS* pPresentationParameters, IDirect3DDevice9** ppReturnedDeviceInterface);
46+
9147std::vector<IDirect3D9*> ms_CreatedDirect3D9List;
48+ std::mutex ms_Direct3D9ListMutex;
9249bool CreateDeviceSecondCallCheck (HRESULT& hOutResult, IDirect3D9* pDirect3D, UINT Adapter, D3DDEVTYPE DeviceType, HWND hFocusWindow, DWORD BehaviorFlags,
9350 D3DPRESENT_PARAMETERS* pPresentationParameters, IDirect3DDevice9** ppReturnedDeviceInterface);
9451void ApplyBorderlessColorCorrection (CProxyDirect3DDevice9* proxyDevice, const D3DPRESENT_PARAMETERS& presentationParameters);
@@ -108,15 +65,15 @@ CProxyDirect3D9::CProxyDirect3D9(IDirect3D9* pInterface)
10865 return ;
10966 }
11067
111- // Take ownership of the interface pointer
112- // ReplaceInterface will AddRef(), giving us our own reference
113- // Caller retains their reference
114- ReplaceInterface (m_pDevice, pInterface, " CProxyDirect3D9 ctor" );
68+ pInterface->AddRef ();
69+ m_pDevice = pInterface;
11570
71+ // Track this Direct3D9 instance for StaticGetDirect3D() lookups
11672 if (m_pDevice)
11773 {
11874 if (IsValidComInterfacePointer (m_pDevice, ComPtrValidation::ValidationMode::ForceRefresh))
11975 {
76+ std::lock_guard<std::mutex> lock (ms_Direct3D9ListMutex);
12077 ms_CreatedDirect3D9List.push_back (m_pDevice);
12178 }
12279 else
@@ -131,8 +88,11 @@ CProxyDirect3D9::CProxyDirect3D9(IDirect3D9* pInterface)
13188CProxyDirect3D9::~CProxyDirect3D9 ()
13289{
13390 WriteDebugEvent (SString (" CProxyDirect3D9::~CProxyDirect3D9 %08x" , this ));
134- ListRemove (ms_CreatedDirect3D9List, m_pDevice);
135- ReleaseInterface (m_pDevice, " CProxyDirect3D9 dtor" );
91+ {
92+ std::lock_guard<std::mutex> lock (ms_Direct3D9ListMutex);
93+ ListRemove (ms_CreatedDirect3D9List, m_pDevice);
94+ }
95+ ReleaseInterface (m_pDevice, 8752 );
13696}
13797
13898/* ** IUnknown methods ***/
@@ -150,7 +110,7 @@ HRESULT CProxyDirect3D9::QueryInterface(REFIID riid, void** ppvObj)
150110
151111ULONG CProxyDirect3D9::AddRef ()
152112{
153- LONG lNewRefCount = InterlockedIncrement (& m_lRefCount) ;
113+ LONG lNewRefCount = m_lRefCount. fetch_add ( 1 , std::memory_order_relaxed) + 1 ;
154114
155115 if (m_pDevice)
156116 m_pDevice->AddRef ();
@@ -160,7 +120,7 @@ ULONG CProxyDirect3D9::AddRef()
160120
161121ULONG CProxyDirect3D9::Release ()
162122{
163- LONG lNewRefCount = InterlockedDecrement (& m_lRefCount) ;
123+ LONG lNewRefCount = m_lRefCount. fetch_sub ( 1 , std::memory_order_acq_rel) - 1 ;
164124
165125 if (lNewRefCount < 0 )
166126 {
@@ -276,6 +236,7 @@ HMONITOR CProxyDirect3D9::GetAdapterMonitor(UINT Adapter)
276236
277237HMONITOR CProxyDirect3D9::StaticGetAdapterMonitor (UINT Adapter)
278238{
239+ std::lock_guard<std::mutex> lock (ms_Direct3D9ListMutex);
279240 IDirect3D9* pDirect3D = GetFirstValidTrackedDirect3D (ms_CreatedDirect3D9List);
280241 if (!pDirect3D)
281242 return NULL ;
@@ -285,6 +246,7 @@ HMONITOR CProxyDirect3D9::StaticGetAdapterMonitor(UINT Adapter)
285246
286247IDirect3D9* CProxyDirect3D9::StaticGetDirect3D ()
287248{
249+ std::lock_guard<std::mutex> lock (ms_Direct3D9ListMutex);
288250 return GetFirstValidTrackedDirect3D (ms_CreatedDirect3D9List);
289251}
290252
@@ -406,7 +368,7 @@ HRESULT CProxyDirect3D9::CreateDevice(UINT Adapter, D3DDEVTYPE DeviceType, HWND
406368 SString message;
407369 message.Format (" CProxyDirect3D9::CreateDevice - rejected invalid IDirect3DDevice9 pointer %p" , pCreatedDevice);
408370 AddReportLog (8755 , message, 5 );
409- ReleaseInterface (pCreatedDevice, " CProxyDirect3D9::CreateDevice invalid return" );
371+ ReleaseInterface (pCreatedDevice, 8755 , " CProxyDirect3D9::CreateDevice invalid return" );
410372 *ppReturnedDeviceInterface = nullptr ;
411373 hResult = D3DERR_INVALIDDEVICE;
412374 }
@@ -620,7 +582,7 @@ HRESULT CreateDeviceInsist(uint uiMinTries, uint uiTimeout, IDirect3D9* pDirect3
620582 SString message;
621583 message.Format (" CreateDeviceInsist: rejected invalid IDirect3DDevice9 pointer %p" , pCreatedDevice);
622584 AddReportLog (8755 , message, 5 );
623- ReleaseInterface (pCreatedDevice, " CreateDeviceInsist invalid return" );
585+ ReleaseInterface (pCreatedDevice, 8755 , " CreateDeviceInsist invalid return" );
624586 *ppReturnedDeviceInterface = nullptr ;
625587 hResult = D3DERR_INVALIDDEVICE;
626588 }
@@ -902,7 +864,7 @@ void AddCapsReport(UINT Adapter, IDirect3D9* pDirect3D, IDirect3DDevice9* pD3DDe
902864 }
903865 }
904866
905- ReleaseInterface (pDirect3DOther, " AddCapsReport GetDirect3D" );
867+ ReleaseInterface (pDirect3DOther, 8799 , " AddCapsReport GetDirect3D" );
906868
907869 // Get caps from D3D
908870 D3DCAPS9 D3DCaps9;
@@ -936,7 +898,7 @@ void AddCapsReport(UINT Adapter, IDirect3D9* pDirect3D, IDirect3DDevice9* pD3DDe
936898 VertexElements[0 ].Type = DeclTypesList[i].VertexType ;
937899 IDirect3DVertexDeclaration9* pD3DVertexDecl = nullptr ;
938900 hr = pD3DDevice9->CreateVertexDeclaration (VertexElements, &pD3DVertexDecl);
939- ReleaseInterface (pD3DVertexDecl, " AddCapsReport CreateVertexDeclaration" );
901+ ReleaseInterface (pD3DVertexDecl, 8799 , " AddCapsReport CreateVertexDeclaration" );
940902
941903 // Check against device caps
942904 bool bCapsSaysOk = (DeviceCaps9.DeclTypes & DeclTypesList[i].CapsType ) ? true : false ;
@@ -1086,7 +1048,7 @@ HRESULT HandleCreateDeviceResult(HRESULT hResult, IDirect3D9* pDirect3D, UINT Ad
10861048 SString message;
10871049 message.Format (" HandleCreateDeviceResult: rejected invalid IDirect3DDevice9 pointer %p" , pCreatedDevice);
10881050 AddReportLog (8755 , message, 5 );
1089- ReleaseInterface (pCreatedDevice, " HandleCreateDeviceResult invalid return" );
1051+ ReleaseInterface (pCreatedDevice, 8755 , " HandleCreateDeviceResult invalid return" );
10901052 *ppReturnedDeviceInterface = nullptr ;
10911053 hResult = D3DERR_INVALIDDEVICE;
10921054 }
@@ -1218,7 +1180,7 @@ void CCore::OnPreCreateDevice(IDirect3D9* pDirect3D, UINT Adapter, D3DDEVTYPE De
12181180 WriteDebugEvent (ToString (Adapter, DeviceType, hFocusWindow, BehaviorFlags, *pPresentationParameters));
12191181 IDirect3DDevice9* pReturnedDeviceInterface = NULL ;
12201182 HRESULT hResult = pDirect3D->CreateDevice (Adapter, DeviceType, hFocusWindow, BehaviorFlags, pPresentationParameters, &pReturnedDeviceInterface);
1221- ReleaseInterface (pReturnedDeviceInterface, " CCore::OnPreCreateDevice temp release" );
1183+ ReleaseInterface (pReturnedDeviceInterface, 8799 , " CCore::OnPreCreateDevice temp release" );
12221184 WriteDebugEvent (SString (" Unmodified result is: %08x" , hResult));
12231185 }
12241186
@@ -1298,7 +1260,7 @@ HRESULT CCore::OnPostCreateDevice(HRESULT hResult, IDirect3D9* pDirect3D, UINT A
12981260
12991261 AddCapsReport (Adapter, pDirect3D, pDevice, false );
13001262
1301- ReleaseInterface (pDevice, " CCore::OnPostCreateDevice temp release" );
1263+ ReleaseInterface (pDevice, 8799 , " CCore::OnPostCreateDevice temp release" );
13021264 *ppReturnedDeviceInterface = pDevice;
13031265
13041266 //
@@ -1341,7 +1303,7 @@ HRESULT CCore::OnPostCreateDevice(HRESULT hResult, IDirect3D9* pDirect3D, UINT A
13411303 {
13421304 AddReportLog (8755 ,
13431305 SString (" CCore::OnPostCreateDevice: rejected invalid IDirect3DDevice9 pointer %p" , pCreatedDevice), 5 );
1344- ReleaseInterface (pCreatedDevice, " CCore::OnPostCreateDevice invalid return" );
1306+ ReleaseInterface (pCreatedDevice, 8755 , " CCore::OnPostCreateDevice invalid return" );
13451307 *ppReturnedDeviceInterface = nullptr ;
13461308 hResult = D3DERR_INVALIDDEVICE;
13471309 }
0 commit comments