Commit def07b3f authored by Nikolay Sivov's avatar Nikolay Sivov Committed by Alexandre Julliard

mfplat: Implement shared device manager API.

parent 3e3490be
......@@ -8553,6 +8553,16 @@ HRESULT WINAPI CreatePropertyStore(IPropertyStore **store)
return S_OK;
}
struct shared_dxgi_manager
{
IMFDXGIDeviceManager *manager;
unsigned int token;
unsigned int locks;
};
static struct shared_dxgi_manager shared_dm;
static CRITICAL_SECTION shared_dm_cs = { NULL, -1, 0, 0, 0, 0 };
enum dxgi_device_handle_flags
{
DXGI_DEVICE_HANDLE_FLAG_OPEN = 0x1,
......@@ -8904,6 +8914,9 @@ static const IMFDXGIDeviceManagerVtbl dxgi_device_manager_vtbl =
dxgi_device_manager_UnlockDevice,
};
/***********************************************************************
* MFCreateDXGIDeviceManager (mfplat.@)
*/
HRESULT WINAPI MFCreateDXGIDeviceManager(UINT *token, IMFDXGIDeviceManager **manager)
{
struct dxgi_device_manager *object;
......@@ -8930,6 +8943,58 @@ HRESULT WINAPI MFCreateDXGIDeviceManager(UINT *token, IMFDXGIDeviceManager **man
return S_OK;
}
/***********************************************************************
* MFLockDXGIDeviceManager (mfplat.@)
*/
HRESULT WINAPI MFLockDXGIDeviceManager(UINT *token, IMFDXGIDeviceManager **manager)
{
HRESULT hr = S_OK;
TRACE("%p, %p.\n", token, manager);
EnterCriticalSection(&shared_dm_cs);
if (!shared_dm.manager)
hr = MFCreateDXGIDeviceManager(&shared_dm.token, &shared_dm.manager);
if (SUCCEEDED(hr))
{
*manager = shared_dm.manager;
IMFDXGIDeviceManager_AddRef(*manager);
shared_dm.locks++;
if (token) *token = shared_dm.token;
}
LeaveCriticalSection(&shared_dm_cs);
return hr;
}
/***********************************************************************
* MFUnlockDXGIDeviceManager (mfplat.@)
*/
HRESULT WINAPI MFUnlockDXGIDeviceManager(void)
{
TRACE("\n");
EnterCriticalSection(&shared_dm_cs);
if (shared_dm.manager)
{
IMFDXGIDeviceManager_Release(shared_dm.manager);
if (!--shared_dm.locks)
{
shared_dm.manager = NULL;
shared_dm.token = 0;
}
}
LeaveCriticalSection(&shared_dm_cs);
return S_OK;
}
/*
* MFllMulDiv implementation is derived from gstreamer utility functions code (gstutils.c),
......
......@@ -131,6 +131,7 @@
@ stdcall MFInvokeCallback(ptr)
@ stub MFJoinIoPort
@ stdcall MFJoinWorkQueue(long long ptr) rtworkq.RtwqJoinWorkQueue
@ stdcall MFLockDXGIDeviceManager(ptr ptr)
@ stdcall MFLockPlatform() rtworkq.RtwqLockPlatform
@ stdcall MFLockSharedWorkQueue(wstr long ptr ptr) rtworkq.RtwqLockSharedWorkQueue
@ stdcall MFLockWorkQueue(long) rtworkq.RtwqLockWorkQueue
......@@ -171,6 +172,7 @@
@ stub MFTraceFuncEnter
@ stub MFUnblockThread
@ stdcall MFUnjoinWorkQueue(long long) rtworkq.RtwqUnjoinWorkQueue
@ stdcall MFUnlockDXGIDeviceManager()
@ stdcall MFUnlockPlatform() rtworkq.RtwqUnlockPlatform
@ stdcall MFUnlockWorkQueue(long) rtworkq.RtwqUnlockWorkQueue
@ stdcall MFUnwrapMediaType(ptr ptr)
......
......@@ -262,6 +262,8 @@ static HRESULT (WINAPI *pMFCreateDXGISurfaceBuffer)(REFIID riid, IUnknown *surfa
IMFMediaBuffer **buffer);
static HRESULT (WINAPI *pMFCreateVideoMediaTypeFromSubtype)(const GUID *subtype, IMFVideoMediaType **media_type);
static HRESULT (WINAPI *pMFLockSharedWorkQueue)(const WCHAR *name, LONG base_priority, DWORD *taskid, DWORD *queue);
static HRESULT (WINAPI *pMFLockDXGIDeviceManager)(UINT *token, IMFDXGIDeviceManager **manager);
static HRESULT (WINAPI *pMFUnlockDXGIDeviceManager)(void);
static HWND create_window(void)
{
......@@ -935,6 +937,7 @@ static void init_functions(void)
X(MFCreateVideoSampleAllocatorEx);
X(MFGetPlaneSize);
X(MFGetStrideForBitmapInfoHeader);
X(MFLockDXGIDeviceManager);
X(MFLockSharedWorkQueue);
X(MFMapDX9FormatToDXGIFormat);
X(MFMapDXGIFormatToDX9Format);
......@@ -947,6 +950,7 @@ static void init_functions(void)
X(MFTRegisterLocalByCLSID);
X(MFTUnregisterLocal);
X(MFTUnregisterLocalByCLSID);
X(MFUnlockDXGIDeviceManager);
if ((mod = LoadLibraryA("d3d11.dll")))
{
......@@ -7168,6 +7172,40 @@ static void test_MFllMulDiv(void)
}
}
static void test_shared_dxgi_device_manager(void)
{
IMFDXGIDeviceManager *manager;
HRESULT hr;
UINT token;
if (!pMFLockDXGIDeviceManager)
{
win_skip("Shared DXGI device manager is not supported.\n");
return;
}
hr = pMFUnlockDXGIDeviceManager();
ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
manager = NULL;
hr = pMFLockDXGIDeviceManager(NULL, &manager);
ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
ok(!!manager, "Unexpected instance.\n");
hr = pMFLockDXGIDeviceManager(&token, &manager);
ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
EXPECT_REF(manager, 3);
hr = pMFUnlockDXGIDeviceManager();
ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
EXPECT_REF(manager, 2);
hr = pMFUnlockDXGIDeviceManager();
ok(hr == S_OK, "Unexpected hr %#x.\n", hr);
}
START_TEST(mfplat)
{
char **argv;
......@@ -7233,6 +7271,7 @@ START_TEST(mfplat)
test_sample_allocator();
test_MFMapDX9FormatToDXGIFormat();
test_MFllMulDiv();
test_shared_dxgi_device_manager();
CoUninitialize();
}
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment