Skip to content

Commit 475d97f

Browse files
authored
wasapi: reset stream on invalidated device error (Bug 1426333).
* wasapi: reset stream on invalidated device error. * wasapi: check stream start for error on reconfigure * wasapi: add logs on stream init/destroy * apply review comments
1 parent cc0d538 commit 475d97f

File tree

1 file changed

+32
-2
lines changed

1 file changed

+32
-2
lines changed

src/cubeb_wasapi.cpp

Lines changed: 32 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -615,6 +615,8 @@ refill(cubeb_stream * stm, void * input_buffer, long input_frames_count,
615615
return out_frames;
616616
}
617617

618+
int wasapi_stream_reset_default_device(cubeb_stream * stm);
619+
618620
/* This helper grabs all the frames available from a capture client, put them in
619621
* linear_input_buffer. linear_input_buffer should be cleared before the
620622
* callback exits. This helper does not work with exclusive mode streams. */
@@ -637,6 +639,13 @@ bool get_input_buffer(cubeb_stream * stm)
637639
for (hr = stm->capture_client->GetNextPacketSize(&next);
638640
next > 0;
639641
hr = stm->capture_client->GetNextPacketSize(&next)) {
642+
if (hr == AUDCLNT_E_DEVICE_INVALIDATED) {
643+
// Application can recover from this error. More info
644+
// https://msdn.microsoft.com/en-us/library/windows/desktop/dd316605(v=vs.85).aspx
645+
LOG("Device invalidated error, reset default device");
646+
wasapi_stream_reset_default_device(stm);
647+
return true;
648+
}
640649

641650
if (FAILED(hr)) {
642651
LOG("cannot get next packet size: %lx", hr);
@@ -713,10 +722,19 @@ bool get_output_buffer(cubeb_stream * stm, void *& buffer, size_t & frame_count)
713722
XASSERT(has_output(stm));
714723

715724
hr = stm->output_client->GetCurrentPadding(&padding_out);
725+
if (hr == AUDCLNT_E_DEVICE_INVALIDATED) {
726+
// Application can recover from this error. More info
727+
// https://msdn.microsoft.com/en-us/library/windows/desktop/dd316605(v=vs.85).aspx
728+
LOG("Device invalidated error, reset default device");
729+
wasapi_stream_reset_default_device(stm);
730+
return true;
731+
}
732+
716733
if (FAILED(hr)) {
717734
LOG("Failed to get padding: %lx", hr);
718735
return false;
719736
}
737+
720738
XASSERT(padding_out <= stm->output_buffer_frame_count);
721739

722740
if (stm->draining) {
@@ -996,11 +1014,21 @@ wasapi_stream_render_loop(LPVOID stream)
9961014
}
9971015
XASSERT(stm->output_client || stm->input_client);
9981016
if (stm->output_client) {
999-
stm->output_client->Start();
1017+
hr = stm->output_client->Start();
1018+
if (FAILED(hr)) {
1019+
LOG("Error starting output after reconfigure, error: %lx", hr);
1020+
is_playing = false;
1021+
continue;
1022+
}
10001023
LOG("Output started after reconfigure.");
10011024
}
10021025
if (stm->input_client) {
1003-
stm->input_client->Start();
1026+
hr = stm->input_client->Start();
1027+
if (FAILED(hr)) {
1028+
LOG("Error starting input after reconfiguring, error: %lx", hr);
1029+
is_playing = false;
1030+
continue;
1031+
}
10041032
LOG("Input started after reconfigure.");
10051033
}
10061034
break;
@@ -1957,6 +1985,7 @@ wasapi_stream_init(cubeb * context, cubeb_stream ** stream,
19571985

19581986
*stream = stm.release();
19591987

1988+
LOG("Stream init succesfull (%p)", *stream);
19601989
return CUBEB_OK;
19611990
}
19621991

@@ -1986,6 +2015,7 @@ void close_wasapi_stream(cubeb_stream * stm)
19862015
void wasapi_stream_destroy(cubeb_stream * stm)
19872016
{
19882017
XASSERT(stm);
2018+
LOG("Stream destroy (%p)", stm);
19892019

19902020
// Only free stm->emergency_bailout if we could join the thread.
19912021
// If we could not join the thread, stm->emergency_bailout is true

0 commit comments

Comments
 (0)