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
d5e648dc
Commit
d5e648dc
authored
Aug 21, 2013
by
Andrew Eikum
Committed by
Alexandre Julliard
Aug 21, 2013
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
dsound: For capture, use MMDevAPI event API instead of timers.
parent
927324ce
Show whitespace changes
Inline
Side-by-side
Showing
3 changed files
with
70 additions
and
53 deletions
+70
-53
capture.c
dlls/dsound/capture.c
+70
-28
dsound.c
dlls/dsound/dsound.c
+0
-24
dsound_private.h
dlls/dsound/dsound_private.h
+0
-1
No files found.
dlls/dsound/capture.c
View file @
d5e648dc
...
@@ -59,6 +59,8 @@ typedef struct IDirectSoundCaptureBufferImpl
...
@@ -59,6 +59,8 @@ typedef struct IDirectSoundCaptureBufferImpl
/* IDirectSoundNotify fields */
/* IDirectSoundNotify fields */
DSBPOSITIONNOTIFY
*
notifies
;
DSBPOSITIONNOTIFY
*
notifies
;
int
nrofnotifies
;
int
nrofnotifies
;
HANDLE
thread
;
HANDLE
sleepev
;
}
IDirectSoundCaptureBufferImpl
;
}
IDirectSoundCaptureBufferImpl
;
/* DirectSoundCaptureDevice implementation structure */
/* DirectSoundCaptureDevice implementation structure */
...
@@ -72,7 +74,6 @@ struct DirectSoundCaptureDevice
...
@@ -72,7 +74,6 @@ struct DirectSoundCaptureDevice
WAVEFORMATEX
*
pwfx
;
WAVEFORMATEX
*
pwfx
;
IDirectSoundCaptureBufferImpl
*
capture_buffer
;
IDirectSoundCaptureBufferImpl
*
capture_buffer
;
DWORD
state
;
DWORD
state
;
UINT
timerID
;
CRITICAL_SECTION
lock
;
CRITICAL_SECTION
lock
;
IMMDevice
*
mmdevice
;
IMMDevice
*
mmdevice
;
IAudioClient
*
client
;
IAudioClient
*
client
;
...
@@ -80,12 +81,20 @@ struct DirectSoundCaptureDevice
...
@@ -80,12 +81,20 @@ struct DirectSoundCaptureDevice
struct
list
entry
;
struct
list
entry
;
};
};
static
DWORD
WINAPI
DSOUND_capture_thread
(
void
*
user
);
static
void
capturebuffer_destroy
(
IDirectSoundCaptureBufferImpl
*
This
)
static
void
capturebuffer_destroy
(
IDirectSoundCaptureBufferImpl
*
This
)
{
{
if
(
This
->
device
->
state
==
STATE_CAPTURING
)
if
(
This
->
device
->
state
==
STATE_CAPTURING
)
This
->
device
->
state
=
STATE_STOPPING
;
This
->
device
->
state
=
STATE_STOPPING
;
if
(
This
->
thread
){
SetEvent
(
This
->
sleepev
);
WaitForSingleObject
(
This
->
thread
,
INFINITE
);
CloseHandle
(
This
->
thread
);
}
CloseHandle
(
This
->
sleepev
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
if
(
This
->
device
->
client
)
{
if
(
This
->
device
->
client
)
{
...
@@ -739,8 +748,8 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
...
@@ -739,8 +748,8 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
}
}
err
=
IAudioClient_Initialize
(
device
->
client
,
err
=
IAudioClient_Initialize
(
device
->
client
,
AUDCLNT_SHAREMODE_SHARED
,
AUDCLNT_STREAMFLAGS_NOPERSIST
,
AUDCLNT_SHAREMODE_SHARED
,
AUDCLNT_STREAMFLAGS_NOPERSIST
|
AUDCLNT_STREAMFLAGS_EVENTCALLBACK
,
200
*
100000
,
5000
0
,
device
->
pwfx
,
NULL
);
200
*
100000
,
0
,
device
->
pwfx
,
NULL
);
if
(
FAILED
(
err
)){
if
(
FAILED
(
err
)){
WARN
(
"Initialize failed: %08x
\n
"
,
err
);
WARN
(
"Initialize failed: %08x
\n
"
,
err
);
IAudioClient_Release
(
device
->
client
);
IAudioClient_Release
(
device
->
client
);
...
@@ -753,12 +762,27 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
...
@@ -753,12 +762,27 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
return
err
;
return
err
;
}
}
This
->
sleepev
=
CreateEventW
(
NULL
,
0
,
0
,
NULL
);
err
=
IAudioClient_SetEventHandle
(
device
->
client
,
This
->
sleepev
);
if
(
FAILED
(
err
)){
WARN
(
"SetEventHandle failed: %08x
\n
"
,
err
);
IAudioClient_Release
(
device
->
client
);
device
->
client
=
NULL
;
CloseHandle
(
This
->
sleepev
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
This
->
device
->
capture_buffer
=
0
;
HeapFree
(
GetProcessHeap
(),
0
,
This
);
return
err
;
}
err
=
IAudioClient_GetService
(
device
->
client
,
&
IID_IAudioCaptureClient
,
err
=
IAudioClient_GetService
(
device
->
client
,
&
IID_IAudioCaptureClient
,
(
void
**
)
&
device
->
capture
);
(
void
**
)
&
device
->
capture
);
if
(
FAILED
(
err
)){
if
(
FAILED
(
err
)){
WARN
(
"GetService failed: %08x
\n
"
,
err
);
WARN
(
"GetService failed: %08x
\n
"
,
err
);
IAudioClient_Release
(
device
->
client
);
IAudioClient_Release
(
device
->
client
);
device
->
client
=
NULL
;
device
->
client
=
NULL
;
CloseHandle
(
This
->
sleepev
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
This
->
device
->
capture_buffer
=
0
;
This
->
device
->
capture_buffer
=
0
;
HeapFree
(
GetProcessHeap
(),
0
,
This
);
HeapFree
(
GetProcessHeap
(),
0
,
This
);
...
@@ -776,6 +800,7 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
...
@@ -776,6 +800,7 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
device
->
client
=
NULL
;
device
->
client
=
NULL
;
IAudioCaptureClient_Release
(
device
->
capture
);
IAudioCaptureClient_Release
(
device
->
capture
);
device
->
capture
=
NULL
;
device
->
capture
=
NULL
;
CloseHandle
(
This
->
sleepev
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
HeapFree
(
GetProcessHeap
(),
0
,
This
->
pdscbd
);
This
->
device
->
capture_buffer
=
0
;
This
->
device
->
capture_buffer
=
0
;
HeapFree
(
GetProcessHeap
(),
0
,
This
);
HeapFree
(
GetProcessHeap
(),
0
,
This
);
...
@@ -783,6 +808,7 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
...
@@ -783,6 +808,7 @@ static HRESULT IDirectSoundCaptureBufferImpl_Create(
}
}
device
->
buffer
=
newbuf
;
device
->
buffer
=
newbuf
;
device
->
buflen
=
buflen
;
device
->
buflen
=
buflen
;
This
->
thread
=
CreateThread
(
NULL
,
0
,
DSOUND_capture_thread
,
This
,
0
,
NULL
);
}
}
IDirectSoundCaptureBuffer_AddRef
(
&
This
->
IDirectSoundCaptureBuffer8_iface
);
IDirectSoundCaptureBuffer_AddRef
(
&
This
->
IDirectSoundCaptureBuffer8_iface
);
...
@@ -830,9 +856,6 @@ static ULONG DirectSoundCaptureDevice_Release(
...
@@ -830,9 +856,6 @@ static ULONG DirectSoundCaptureDevice_Release(
if
(
!
ref
)
{
if
(
!
ref
)
{
TRACE
(
"deleting object
\n
"
);
TRACE
(
"deleting object
\n
"
);
timeKillEvent
(
device
->
timerID
);
timeEndPeriod
(
DS_TIME_RES
);
EnterCriticalSection
(
&
DSOUND_capturers_lock
);
EnterCriticalSection
(
&
DSOUND_capturers_lock
);
list_remove
(
&
device
->
entry
);
list_remove
(
&
device
->
entry
);
LeaveCriticalSection
(
&
DSOUND_capturers_lock
);
LeaveCriticalSection
(
&
DSOUND_capturers_lock
);
...
@@ -851,29 +874,19 @@ static ULONG DirectSoundCaptureDevice_Release(
...
@@ -851,29 +874,19 @@ static ULONG DirectSoundCaptureDevice_Release(
return
ref
;
return
ref
;
}
}
static
void
CALLBACK
DSOUND_capture_timer
(
UINT
timerID
,
UINT
msg
,
DWORD_PTR
user
,
static
HRESULT
DSOUND_capture_data
(
DirectSoundCaptureDevice
*
device
)
DWORD_PTR
dw1
,
DWORD_PTR
dw2
)
{
{
DirectSoundCaptureDevice
*
device
=
(
DirectSoundCaptureDevice
*
)
use
r
;
HRESULT
h
r
;
UINT32
packet_frames
,
packet_bytes
,
avail_bytes
,
skip_bytes
=
0
;
UINT32
packet_frames
,
packet_bytes
,
avail_bytes
,
skip_bytes
=
0
;
DWORD
flags
;
DWORD
flags
;
BYTE
*
buf
;
BYTE
*
buf
;
HRESULT
hr
;
if
(
!
device
->
ref
)
if
(
!
device
->
capture_buffer
||
device
->
state
==
STATE_STOPPED
)
return
;
return
S_FALSE
;
EnterCriticalSection
(
&
device
->
lock
);
if
(
!
device
->
capture_buffer
||
device
->
state
==
STATE_STOPPED
){
LeaveCriticalSection
(
&
device
->
lock
);
return
;
}
if
(
device
->
state
==
STATE_STOPPING
){
if
(
device
->
state
==
STATE_STOPPING
){
device
->
state
=
STATE_STOPPED
;
device
->
state
=
STATE_STOPPED
;
LeaveCriticalSection
(
&
device
->
lock
);
return
S_FALSE
;
return
;
}
}
if
(
device
->
state
==
STATE_STARTING
)
if
(
device
->
state
==
STATE_STARTING
)
...
@@ -882,9 +895,8 @@ static void CALLBACK DSOUND_capture_timer(UINT timerID, UINT msg, DWORD_PTR user
...
@@ -882,9 +895,8 @@ static void CALLBACK DSOUND_capture_timer(UINT timerID, UINT msg, DWORD_PTR user
hr
=
IAudioCaptureClient_GetBuffer
(
device
->
capture
,
&
buf
,
&
packet_frames
,
hr
=
IAudioCaptureClient_GetBuffer
(
device
->
capture
,
&
buf
,
&
packet_frames
,
&
flags
,
NULL
,
NULL
);
&
flags
,
NULL
,
NULL
);
if
(
FAILED
(
hr
)){
if
(
FAILED
(
hr
)){
LeaveCriticalSection
(
&
device
->
lock
);
WARN
(
"GetBuffer failed: %08x
\n
"
,
hr
);
WARN
(
"GetBuffer failed: %08x
\n
"
,
hr
);
return
;
return
hr
;
}
}
packet_bytes
=
packet_frames
*
device
->
pwfx
->
nBlockAlign
;
packet_bytes
=
packet_frames
*
device
->
pwfx
->
nBlockAlign
;
...
@@ -917,12 +929,44 @@ static void CALLBACK DSOUND_capture_timer(UINT timerID, UINT msg, DWORD_PTR user
...
@@ -917,12 +929,44 @@ static void CALLBACK DSOUND_capture_timer(UINT timerID, UINT msg, DWORD_PTR user
hr
=
IAudioCaptureClient_ReleaseBuffer
(
device
->
capture
,
packet_frames
);
hr
=
IAudioCaptureClient_ReleaseBuffer
(
device
->
capture
,
packet_frames
);
if
(
FAILED
(
hr
)){
if
(
FAILED
(
hr
)){
LeaveCriticalSection
(
&
device
->
lock
);
WARN
(
"ReleaseBuffer failed: %08x
\n
"
,
hr
);
WARN
(
"ReleaseBuffer failed: %08x
\n
"
,
hr
);
return
;
return
hr
;
}
return
S_OK
;
}
static
DWORD
WINAPI
DSOUND_capture_thread
(
void
*
user
)
{
IDirectSoundCaptureBufferImpl
*
buffer
=
user
;
HRESULT
hr
;
DWORD
ret
,
wait_ms
;
REFERENCE_TIME
period
;
hr
=
IAudioClient_GetDevicePeriod
(
buffer
->
device
->
client
,
&
period
,
NULL
);
if
(
FAILED
(
hr
)){
WARN
(
"GetDevicePeriod failed: %08x
\n
"
,
hr
);
wait_ms
=
5
;
}
else
wait_ms
=
MulDiv
(
5
,
period
,
10000
);
while
(
buffer
->
ref
){
ret
=
WaitForSingleObject
(
buffer
->
sleepev
,
wait_ms
);
if
(
!
buffer
->
device
->
ref
)
break
;
if
(
ret
==
WAIT_OBJECT_0
){
EnterCriticalSection
(
&
buffer
->
device
->
lock
);
DSOUND_capture_data
(
buffer
->
device
);
LeaveCriticalSection
(
&
buffer
->
device
->
lock
);
}
else
if
(
ret
!=
WAIT_TIMEOUT
)
WARN
(
"WaitForSingleObject failed: %u
\n
"
,
GetLastError
());
}
}
LeaveCriticalSection
(
&
device
->
lock
)
;
return
0
;
}
}
static
struct
_TestFormat
{
static
struct
_TestFormat
{
...
@@ -1020,8 +1064,6 @@ static HRESULT DirectSoundCaptureDevice_Initialize(
...
@@ -1020,8 +1064,6 @@ static HRESULT DirectSoundCaptureDevice_Initialize(
}
}
IAudioClient_Release
(
client
);
IAudioClient_Release
(
client
);
device
->
timerID
=
DSOUND_create_timer
(
DSOUND_capture_timer
,
(
DWORD_PTR
)
device
);
list_add_tail
(
&
DSOUND_capturers
,
&
device
->
entry
);
list_add_tail
(
&
DSOUND_capturers
,
&
device
->
entry
);
*
ppDevice
=
device
;
*
ppDevice
=
device
;
...
...
dlls/dsound/dsound.c
View file @
d5e648dc
...
@@ -735,30 +735,6 @@ BOOL DSOUND_check_supported(IAudioClient *client, DWORD rate,
...
@@ -735,30 +735,6 @@ BOOL DSOUND_check_supported(IAudioClient *client, DWORD rate,
return
hr
==
S_OK
;
return
hr
==
S_OK
;
}
}
UINT
DSOUND_create_timer
(
LPTIMECALLBACK
cb
,
DWORD_PTR
user
)
{
UINT
triggertime
=
DS_TIME_DEL
,
res
=
DS_TIME_RES
,
id
;
TIMECAPS
time
;
timeGetDevCaps
(
&
time
,
sizeof
(
TIMECAPS
));
TRACE
(
"Minimum timer resolution: %u, max timer: %u
\n
"
,
time
.
wPeriodMin
,
time
.
wPeriodMax
);
if
(
triggertime
<
time
.
wPeriodMin
)
triggertime
=
time
.
wPeriodMin
;
if
(
res
<
time
.
wPeriodMin
)
res
=
time
.
wPeriodMin
;
if
(
timeBeginPeriod
(
res
)
==
TIMERR_NOCANDO
)
WARN
(
"Could not set minimum resolution, don't expect sound
\n
"
);
id
=
timeSetEvent
(
triggertime
,
res
,
cb
,
user
,
TIME_PERIODIC
|
TIME_KILL_SYNCHRONOUS
);
if
(
!
id
)
{
WARN
(
"Timer not created! Retrying without TIME_KILL_SYNCHRONOUS
\n
"
);
id
=
timeSetEvent
(
triggertime
,
res
,
cb
,
user
,
TIME_PERIODIC
);
if
(
!
id
)
ERR
(
"Could not create timer, sound playback will not occur
\n
"
);
}
return
id
;
}
HRESULT
DirectSoundDevice_Initialize
(
DirectSoundDevice
**
ppDevice
,
LPCGUID
lpcGUID
)
HRESULT
DirectSoundDevice_Initialize
(
DirectSoundDevice
**
ppDevice
,
LPCGUID
lpcGUID
)
{
{
HRESULT
hr
=
DS_OK
;
HRESULT
hr
=
DS_OK
;
...
...
dlls/dsound/dsound_private.h
View file @
d5e648dc
...
@@ -261,6 +261,5 @@ HRESULT get_mmdevice(EDataFlow flow, const GUID *tgt, IMMDevice **device) DECLSP
...
@@ -261,6 +261,5 @@ HRESULT get_mmdevice(EDataFlow flow, const GUID *tgt, IMMDevice **device) DECLSP
BOOL
DSOUND_check_supported
(
IAudioClient
*
client
,
DWORD
rate
,
BOOL
DSOUND_check_supported
(
IAudioClient
*
client
,
DWORD
rate
,
DWORD
depth
,
WORD
channels
)
DECLSPEC_HIDDEN
;
DWORD
depth
,
WORD
channels
)
DECLSPEC_HIDDEN
;
UINT
DSOUND_create_timer
(
LPTIMECALLBACK
cb
,
DWORD_PTR
user
)
DECLSPEC_HIDDEN
;
HRESULT
enumerate_mmdevices
(
EDataFlow
flow
,
GUID
*
guids
,
HRESULT
enumerate_mmdevices
(
EDataFlow
flow
,
GUID
*
guids
,
LPDSENUMCALLBACKW
cb
,
void
*
user
)
DECLSPEC_HIDDEN
;
LPDSENUMCALLBACKW
cb
,
void
*
user
)
DECLSPEC_HIDDEN
;
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