Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wine-winehq
Project
Project
Details
Activity
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Registry
Registry
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
wine
wine-winehq
Commits
431324ba
Commit
431324ba
authored
Jun 30, 2020
by
Nikolay Sivov
Committed by
Alexandre Julliard
Jun 30, 2020
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
dxva2: Implement locking functionality in device manager.
Signed-off-by:
Nikolay Sivov
<
nsivov@codeweavers.com
>
Signed-off-by:
Alexandre Julliard
<
julliard@winehq.org
>
parent
b61455cb
Hide whitespace changes
Inline
Side-by-side
Showing
2 changed files
with
199 additions
and
5 deletions
+199
-5
main.c
dlls/dxva2/main.c
+90
-4
dxva2.c
dlls/dxva2/tests/dxva2.c
+109
-1
No files found.
dlls/dxva2/main.c
View file @
431324ba
...
...
@@ -42,6 +42,7 @@ enum device_handle_flags
struct
device_handle
{
unsigned
int
flags
;
IDirect3DStateBlock9
*
state_block
;
};
struct
device_manager
...
...
@@ -57,7 +58,10 @@ struct device_manager
size_t
count
;
size_t
capacity
;
HANDLE
locking_handle
;
CRITICAL_SECTION
cs
;
CONDITION_VARIABLE
lock
;
};
static
BOOL
dxva_array_reserve
(
void
**
elements
,
size_t
*
capacity
,
size_t
count
,
size_t
size
)
...
...
@@ -254,6 +258,7 @@ static ULONG WINAPI device_manager_Release(IDirect3DDeviceManager9 *iface)
{
struct
device_manager
*
manager
=
impl_from_IDirect3DDeviceManager9
(
iface
);
ULONG
refcount
=
InterlockedDecrement
(
&
manager
->
refcount
);
size_t
i
;
TRACE
(
"%p, refcount %u.
\n
"
,
iface
,
refcount
);
...
...
@@ -262,6 +267,11 @@ static ULONG WINAPI device_manager_Release(IDirect3DDeviceManager9 *iface)
if
(
manager
->
device
)
IDirect3DDevice9_Release
(
manager
->
device
);
DeleteCriticalSection
(
&
manager
->
cs
);
for
(
i
=
0
;
i
<
manager
->
count
;
++
i
)
{
if
(
manager
->
handles
[
i
].
state_block
)
IDirect3DStateBlock9_Release
(
manager
->
handles
[
i
].
state_block
);
}
heap_free
(
manager
->
handles
);
heap_free
(
manager
);
}
...
...
@@ -284,13 +294,21 @@ static HRESULT WINAPI device_manager_ResetDevice(IDirect3DDeviceManager9 *iface,
if
(
manager
->
device
)
{
for
(
i
=
0
;
i
<
manager
->
count
;
++
i
)
{
if
(
manager
->
handles
[
i
].
state_block
)
IDirect3DStateBlock9_Release
(
manager
->
handles
[
i
].
state_block
);
manager
->
handles
[
i
].
state_block
=
NULL
;
manager
->
handles
[
i
].
flags
|=
HANDLE_FLAG_INVALID
;
}
manager
->
locking_handle
=
NULL
;
IDirect3DDevice9_Release
(
manager
->
device
);
}
manager
->
device
=
device
;
IDirect3DDevice9_AddRef
(
manager
->
device
);
LeaveCriticalSection
(
&
manager
->
cs
);
WakeAllConditionVariable
(
&
manager
->
lock
);
return
S_OK
;
}
...
...
@@ -324,6 +342,7 @@ static HRESULT WINAPI device_manager_OpenDeviceHandle(IDirect3DDeviceManager9 *i
{
*
hdevice
=
ULongToHandle
(
manager
->
count
+
1
);
manager
->
handles
[
manager
->
count
].
flags
|=
HANDLE_FLAG_OPEN
;
manager
->
handles
[
manager
->
count
].
state_block
=
NULL
;
manager
->
count
++
;
}
else
...
...
@@ -355,15 +374,22 @@ static HRESULT WINAPI device_manager_CloseDeviceHandle(IDirect3DDeviceManager9 *
{
if
(
manager
->
handles
[
idx
].
flags
&
HANDLE_FLAG_OPEN
)
{
if
(
manager
->
locking_handle
==
hdevice
)
manager
->
locking_handle
=
NULL
;
manager
->
handles
[
idx
].
flags
=
0
;
if
(
idx
==
manager
->
count
-
1
)
manager
->
count
--
;
if
(
manager
->
handles
[
idx
].
state_block
)
IDirect3DStateBlock9_Release
(
manager
->
handles
[
idx
].
state_block
);
manager
->
handles
[
idx
].
state_block
=
NULL
;
}
else
hr
=
E_HANDLE
;
}
LeaveCriticalSection
(
&
manager
->
cs
);
WakeAllConditionVariable
(
&
manager
->
lock
);
return
hr
;
}
...
...
@@ -393,16 +419,75 @@ static HRESULT WINAPI device_manager_TestDevice(IDirect3DDeviceManager9 *iface,
static
HRESULT
WINAPI
device_manager_LockDevice
(
IDirect3DDeviceManager9
*
iface
,
HANDLE
hdevice
,
IDirect3DDevice9
**
device
,
BOOL
block
)
{
FIXME
(
"%p, %p, %p, %d.
\n
"
,
iface
,
hdevice
,
device
,
block
);
struct
device_manager
*
manager
=
impl_from_IDirect3DDeviceManager9
(
iface
);
HRESULT
hr
;
size_t
idx
;
return
E_NOTIMPL
;
TRACE
(
"%p, %p, %p, %d.
\n
"
,
iface
,
hdevice
,
device
,
block
);
EnterCriticalSection
(
&
manager
->
cs
);
if
(
!
manager
->
device
)
hr
=
DXVA2_E_NOT_INITIALIZED
;
else
if
(
SUCCEEDED
(
hr
=
device_manager_get_handle_index
(
manager
,
hdevice
,
&
idx
)))
{
if
(
manager
->
locking_handle
&&
!
block
)
hr
=
DXVA2_E_VIDEO_DEVICE_LOCKED
;
else
{
while
(
manager
->
locking_handle
&&
block
)
{
SleepConditionVariableCS
(
&
manager
->
lock
,
&
manager
->
cs
,
INFINITE
);
}
if
(
SUCCEEDED
(
hr
=
device_manager_get_handle_index
(
manager
,
hdevice
,
&
idx
)))
{
if
(
manager
->
handles
[
idx
].
flags
&
HANDLE_FLAG_INVALID
)
hr
=
DXVA2_E_NEW_VIDEO_DEVICE
;
else
{
if
(
manager
->
handles
[
idx
].
state_block
)
{
if
(
FAILED
(
IDirect3DStateBlock9_Apply
(
manager
->
handles
[
idx
].
state_block
)))
WARN
(
"Failed to apply state.
\n
"
);
IDirect3DStateBlock9_Release
(
manager
->
handles
[
idx
].
state_block
);
manager
->
handles
[
idx
].
state_block
=
NULL
;
}
*
device
=
manager
->
device
;
IDirect3DDevice9_AddRef
(
*
device
);
manager
->
locking_handle
=
hdevice
;
}
}
}
}
LeaveCriticalSection
(
&
manager
->
cs
);
return
hr
;
}
static
HRESULT
WINAPI
device_manager_UnlockDevice
(
IDirect3DDeviceManager9
*
iface
,
HANDLE
hdevice
,
BOOL
savestate
)
{
FIXME
(
"%p, %p, %d.
\n
"
,
iface
,
hdevice
,
savestate
);
struct
device_manager
*
manager
=
impl_from_IDirect3DDeviceManager9
(
iface
);
HRESULT
hr
;
size_t
idx
;
return
E_NOTIMPL
;
TRACE
(
"%p, %p, %d.
\n
"
,
iface
,
hdevice
,
savestate
);
EnterCriticalSection
(
&
manager
->
cs
);
if
(
hdevice
!=
manager
->
locking_handle
)
hr
=
E_INVALIDARG
;
else
if
(
SUCCEEDED
(
hr
=
device_manager_get_handle_index
(
manager
,
hdevice
,
&
idx
)))
{
manager
->
locking_handle
=
NULL
;
if
(
savestate
)
IDirect3DDevice9_CreateStateBlock
(
manager
->
device
,
D3DSBT_ALL
,
&
manager
->
handles
[
idx
].
state_block
);
}
LeaveCriticalSection
(
&
manager
->
cs
);
WakeAllConditionVariable
(
&
manager
->
lock
);
return
hr
;
}
static
HRESULT
WINAPI
device_manager_GetVideoService
(
IDirect3DDeviceManager9
*
iface
,
HANDLE
hdevice
,
REFIID
riid
,
...
...
@@ -470,6 +555,7 @@ HRESULT WINAPI DXVA2CreateDirect3DDeviceManager9(UINT *token, IDirect3DDeviceMan
object
->
refcount
=
1
;
object
->
token
=
GetTickCount
();
InitializeCriticalSection
(
&
object
->
cs
);
InitializeConditionVariable
(
&
object
->
lock
);
*
token
=
object
->
token
;
*
manager
=
&
object
->
IDirect3DDeviceManager9_iface
;
...
...
dlls/dxva2/tests/dxva2.c
View file @
431324ba
...
...
@@ -72,6 +72,7 @@ static void test_device_manager(void)
HWND
window
;
UINT
token
;
HRESULT
hr
;
RECT
rect
;
window
=
create_window
();
d3d
=
Direct3DCreate9
(
D3D_SDK_VERSION
);
...
...
@@ -88,13 +89,15 @@ static void test_device_manager(void)
hr
=
IDirect3DDeviceManager9_OpenDeviceHandle
(
manager
,
&
handle
);
ok
(
hr
==
DXVA2_E_NOT_INITIALIZED
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
0
,
&
device2
,
FALSE
);
ok
(
hr
==
DXVA2_E_NOT_INITIALIZED
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* Invalid token. */
hr
=
IDirect3DDeviceManager9_ResetDevice
(
manager
,
device
,
token
+
1
);
ok
(
hr
==
E_INVALIDARG
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_ResetDevice
(
manager
,
device
,
token
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
refcount
=
get_refcount
((
IUnknown
*
)
device
);
handle1
=
NULL
;
...
...
@@ -140,6 +143,7 @@ static void test_device_manager(void)
IDirectXVideoProcessorService_Release
(
processor_service
);
device2
=
create_device
(
d3d
,
window
);
hr
=
IDirect3DDeviceManager9_ResetDevice
(
manager
,
device2
,
token
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
...
...
@@ -150,6 +154,110 @@ static void test_device_manager(void)
hr
=
IDirect3DDeviceManager9_TestDevice
(
manager
,
handle
);
ok
(
hr
==
DXVA2_E_NEW_VIDEO_DEVICE
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_CloseDeviceHandle
(
manager
,
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* Lock/Unlock. */
hr
=
IDirect3DDeviceManager9_OpenDeviceHandle
(
manager
,
&
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle
,
&
device3
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
ok
(
device2
==
device3
,
"Unexpected device pointer.
\n
"
);
IDirect3DDevice9_Release
(
device3
);
hr
=
IDirect3DDeviceManager9_UnlockDevice
(
manager
,
handle
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_UnlockDevice
(
manager
,
handle
,
FALSE
);
ok
(
hr
==
E_INVALIDARG
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_UnlockDevice
(
manager
,
(
HANDLE
)((
ULONG_PTR
)
handle
+
100
),
FALSE
);
ok
(
hr
==
E_INVALIDARG
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* Locked with one handle, unlock with another. */
hr
=
IDirect3DDeviceManager9_OpenDeviceHandle
(
manager
,
&
handle1
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle
,
&
device3
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
ok
(
device2
==
device3
,
"Unexpected device pointer.
\n
"
);
IDirect3DDevice9_Release
(
device3
);
hr
=
IDirect3DDeviceManager9_UnlockDevice
(
manager
,
handle1
,
FALSE
);
ok
(
hr
==
E_INVALIDARG
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* Closing unlocks the device. */
hr
=
IDirect3DDeviceManager9_CloseDeviceHandle
(
manager
,
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle1
,
&
device3
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
ok
(
device2
==
device3
,
"Unexpected device pointer.
\n
"
);
IDirect3DDevice9_Release
(
device3
);
hr
=
IDirect3DDeviceManager9_CloseDeviceHandle
(
manager
,
handle1
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* Open two handles. */
hr
=
IDirect3DDeviceManager9_OpenDeviceHandle
(
manager
,
&
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_OpenDeviceHandle
(
manager
,
&
handle1
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle
,
&
device3
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
ok
(
device2
==
device3
,
"Unexpected device pointer.
\n
"
);
IDirect3DDevice9_Release
(
device3
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle1
,
&
device3
,
FALSE
);
ok
(
hr
==
DXVA2_E_VIDEO_DEVICE_LOCKED
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_CloseDeviceHandle
(
manager
,
handle1
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_CloseDeviceHandle
(
manager
,
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* State saving function. */
hr
=
IDirect3DDeviceManager9_OpenDeviceHandle
(
manager
,
&
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle
,
&
device3
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
ok
(
device2
==
device3
,
"Unexpected device pointer.
\n
"
);
SetRect
(
&
rect
,
50
,
60
,
70
,
80
);
hr
=
IDirect3DDevice9_SetScissorRect
(
device3
,
&
rect
);
ok
(
SUCCEEDED
(
hr
),
"Failed to set scissor rect, hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_UnlockDevice
(
manager
,
handle
,
TRUE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
SetRect
(
&
rect
,
30
,
60
,
70
,
80
);
hr
=
IDirect3DDevice9_SetScissorRect
(
device3
,
&
rect
);
ok
(
SUCCEEDED
(
hr
),
"Failed to set scissor rect, hr %#x.
\n
"
,
hr
);
IDirect3DDevice9_Release
(
device3
);
hr
=
IDirect3DDeviceManager9_LockDevice
(
manager
,
handle
,
&
device3
,
FALSE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
ok
(
device2
==
device3
,
"Unexpected device pointer.
\n
"
);
hr
=
IDirect3DDevice9_GetScissorRect
(
device3
,
&
rect
);
ok
(
SUCCEEDED
(
hr
),
"Failed to get scissor rect, hr %#x.
\n
"
,
hr
);
ok
(
rect
.
left
==
50
&&
rect
.
top
==
60
&&
rect
.
right
==
70
&&
rect
.
bottom
==
80
,
"Got unexpected scissor rect %s.
\n
"
,
wine_dbgstr_rect
(
&
rect
));
IDirect3DDevice9_Release
(
device3
);
hr
=
IDirect3DDeviceManager9_UnlockDevice
(
manager
,
handle
,
TRUE
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
hr
=
IDirect3DDeviceManager9_CloseDeviceHandle
(
manager
,
handle
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
/* Acceleration service. */
hr
=
DXVA2CreateVideoService
(
device
,
&
IID_IDirectXVideoAccelerationService
,
(
void
**
)
&
accel_service
);
ok
(
hr
==
S_OK
,
"Unexpected hr %#x.
\n
"
,
hr
);
...
...
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment