Anton Baskanov : amstream: Call IMediaStreamFilter::Flush in IPin::BeginFlush.
Alexandre Julliard
julliard at winehq.org
Tue Apr 20 16:27:47 CDT 2021
Module: wine
Branch: master
Commit: 1917fe0e0734df60911739872efcdcbf2c665a68
URL: https://source.winehq.org/git/wine.git/?a=commit;h=1917fe0e0734df60911739872efcdcbf2c665a68
Author: Anton Baskanov <baskanov at gmail.com>
Date: Tue Apr 20 00:22:55 2021 +0700
amstream: Call IMediaStreamFilter::Flush in IPin::BeginFlush.
Signed-off-by: Anton Baskanov <baskanov at gmail.com>
Signed-off-by: Zebediah Figura <z.figura12 at gmail.com>
Signed-off-by: Alexandre Julliard <julliard at winehq.org>
---
dlls/amstream/audiostream.c | 8 ++++++++
dlls/amstream/ddrawstream.c | 8 ++++++++
dlls/amstream/tests/amstream.c | 12 ++++++------
3 files changed, 22 insertions(+), 6 deletions(-)
diff --git a/dlls/amstream/audiostream.c b/dlls/amstream/audiostream.c
index a07e62a4672..77ed4072ccf 100644
--- a/dlls/amstream/audiostream.c
+++ b/dlls/amstream/audiostream.c
@@ -1168,17 +1168,25 @@ static HRESULT WINAPI audio_sink_EndOfStream(IPin *iface)
static HRESULT WINAPI audio_sink_BeginFlush(IPin *iface)
{
struct audio_stream *stream = impl_from_IPin(iface);
+ BOOL cancel_eos;
TRACE("stream %p.\n", stream);
EnterCriticalSection(&stream->cs);
+ cancel_eos = stream->eos;
+
stream->flushing = TRUE;
stream->eos = FALSE;
flush_receive_queue(stream);
LeaveCriticalSection(&stream->cs);
+ /* Calling IMediaStreamFilter::Flush() inside the critical section would
+ * invert the locking order, so we must leave it first to avoid the
+ * application thread deadlocking on the filter's critical section. */
+ IMediaStreamFilter_Flush(stream->filter, cancel_eos);
+
return S_OK;
}
diff --git a/dlls/amstream/ddrawstream.c b/dlls/amstream/ddrawstream.c
index e04e3a1c56f..b1ef12cb524 100644
--- a/dlls/amstream/ddrawstream.c
+++ b/dlls/amstream/ddrawstream.c
@@ -1188,17 +1188,25 @@ static HRESULT WINAPI ddraw_sink_EndOfStream(IPin *iface)
static HRESULT WINAPI ddraw_sink_BeginFlush(IPin *iface)
{
struct ddraw_stream *stream = impl_from_IPin(iface);
+ BOOL cancel_eos;
TRACE("stream %p.\n", stream);
EnterCriticalSection(&stream->cs);
+ cancel_eos = stream->eos;
+
stream->flushing = TRUE;
stream->eos = FALSE;
WakeConditionVariable(&stream->update_queued_cv);
LeaveCriticalSection(&stream->cs);
+ /* Calling IMediaStreamFilter::Flush() inside the critical section would
+ * invert the locking order, so we must leave it first to avoid the
+ * application thread deadlocking on the filter's critical section. */
+ IMediaStreamFilter_Flush(stream->filter, cancel_eos);
+
return S_OK;
}
diff --git a/dlls/amstream/tests/amstream.c b/dlls/amstream/tests/amstream.c
index eaa1073532d..182fb06a082 100644
--- a/dlls/amstream/tests/amstream.c
+++ b/dlls/amstream/tests/amstream.c
@@ -4214,7 +4214,7 @@ static void test_audiostream_begin_flush_end_flush(void)
hr = IPin_EndOfStream(pin2);
ok(hr == S_OK, "Got hr %#x.\n", hr);
- todo_wine ok(graph.got_notify == 0, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
+ ok(graph.got_notify == 0, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
hr = IPin_EndOfStream(pin);
ok(hr == S_OK, "Got hr %#x.\n", hr);
@@ -4248,8 +4248,8 @@ static void test_audiostream_begin_flush_end_flush(void)
hr = IPin_EndOfStream(pin2);
ok(hr == S_OK, "Got hr %#x.\n", hr);
- todo_wine ok(graph.got_notify == 1, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
- todo_wine ok(graph.event_code == EC_COMPLETE, "Got event code %d.\n", graph.event_code);
+ ok(graph.got_notify == 1, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
+ ok(graph.event_code == EC_COMPLETE, "Got event code %d.\n", graph.event_code);
hr = IAMMultiMediaStream_SetState(mmstream, STREAMSTATE_STOP);
ok(hr == S_OK, "Got hr %#x.\n", hr);
@@ -5808,7 +5808,7 @@ static void test_ddrawstream_begin_flush_end_flush(void)
hr = IPin_EndOfStream(pin2);
ok(hr == S_OK, "Got hr %#x.\n", hr);
- todo_wine ok(graph.got_notify == 0, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
+ ok(graph.got_notify == 0, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
hr = IPin_EndOfStream(pin);
ok(hr == S_OK, "Got hr %#x.\n", hr);
@@ -5842,8 +5842,8 @@ static void test_ddrawstream_begin_flush_end_flush(void)
hr = IPin_EndOfStream(pin2);
ok(hr == S_OK, "Got hr %#x.\n", hr);
- todo_wine ok(graph.got_notify == 1, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
- todo_wine ok(graph.event_code == EC_COMPLETE, "Got event code %d.\n", graph.event_code);
+ ok(graph.got_notify == 1, "Got %d calls to IMediaEventSink::Notify().\n", graph.got_notify);
+ ok(graph.event_code == EC_COMPLETE, "Got event code %d.\n", graph.event_code);
hr = IAMMultiMediaStream_SetState(mmstream, STREAMSTATE_STOP);
ok(hr == S_OK, "Got hr %#x.\n", hr);
More information about the wine-cvs
mailing list