This fixes a looping audio issue during seek in VRChat. The issue is that on Windows the stop request in handled immediately thus the AVPro MFT (which loops the audio) can be immediately flushed. Wine currently waits for a pending sample request to be completed before handling the stop request. As a result, the AVPro MFT loops audio whilst it waits for another sample (or to be flushed).
This MR releases the source CS before calling `wg_parser_stream_get_buffer` so it does not delay the handling of the stop request. This appears to be safe as the Unix side of `wg_parser_stream_get_buffer` has its own set of primitives.
From: Brendan McGrath bmcgrath@codeweavers.com
--- dlls/winegstreamer/media_source.c | 16 +++++++++++++++- 1 file changed, 15 insertions(+), 1 deletion(-)
diff --git a/dlls/winegstreamer/media_source.c b/dlls/winegstreamer/media_source.c index ab842b3e438..15f65cb41cb 100644 --- a/dlls/winegstreamer/media_source.c +++ b/dlls/winegstreamer/media_source.c @@ -791,6 +791,20 @@ static HRESULT media_stream_send_eos(struct media_source *source, struct media_s return S_OK; }
+static bool stream_get_buffer(struct media_stream *stream, struct wg_parser_buffer *buffer) +{ + struct media_source *source = impl_from_IMFMediaSource(stream->media_source); + wg_parser_stream_t wg_stream = stream->wg_stream; + wg_parser_t wg_parser = source->wg_parser; + bool ret; + + LeaveCriticalSection(&source->cs); + ret = wg_parser_stream_get_buffer(wg_parser, wg_stream, buffer); + EnterCriticalSection(&source->cs); + + return ret; +} + static HRESULT wait_on_sample(struct media_stream *stream, IUnknown *token) { struct media_source *source = impl_from_IMFMediaSource(stream->media_source); @@ -798,7 +812,7 @@ static HRESULT wait_on_sample(struct media_stream *stream, IUnknown *token)
TRACE("%p, %p\n", stream, token);
- while (wg_parser_stream_get_buffer(source->wg_parser, stream->wg_stream, &buffer)) + while (stream_get_buffer(stream, &buffer)) { HRESULT hr = media_stream_send_sample(stream, &buffer, token); if (hr != S_FALSE)