aboutsummaryrefslogtreecommitdiffhomepage
diff options
context:
space:
mode:
authorMatthew Gregan <[email protected]>2022-03-26 13:50:32 +1300
committerMatthew Gregan <[email protected]>2022-03-30 18:12:01 +1300
commitb62d61bc661b49c7a7f5d97f4657189c630ac7a5 (patch)
treec1d774314a0d474ee8f489ce18f378a4fe1a14ab
parent16c2a521525ae91c376eaa8a49b99ecccd89e066 (diff)
downloadcubeb-b62d61bc661b49c7a7f5d97f4657189c630ac7a5.tar.gz
cubeb-b62d61bc661b49c7a7f5d97f4657189c630ac7a5.zip
audiounit,pulse,wasapi: Handle data_callback errors and signal to user via state_callback.
-rw-r--r--src/cubeb_audiounit.cpp7
-rw-r--r--src/cubeb_pulse.c4
-rw-r--r--src/cubeb_wasapi.cpp29
3 files changed, 31 insertions, 9 deletions
diff --git a/src/cubeb_audiounit.cpp b/src/cubeb_audiounit.cpp
index 8f2741a..37036a3 100644
--- a/src/cubeb_audiounit.cpp
+++ b/src/cubeb_audiounit.cpp
@@ -541,6 +541,13 @@ audiounit_input_callback(void * user_ptr, AudioUnitRenderActionFlags * flags,
long outframes = cubeb_resampler_fill(stm->resampler.get(),
stm->input_linear_buffer->data(),
&total_input_frames, NULL, 0);
+ if (outframes < 0) {
+ stm->shutdown = true;
+ OSStatus r = AudioOutputUnitStop(stm->input_unit);
+ assert(r == 0);
+ stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR);
+ return noErr;
+ }
stm->draining = outframes < total_input_frames;
// Reset input buffer
diff --git a/src/cubeb_pulse.c b/src/cubeb_pulse.c
index 3ed6bdc..13f6791 100644
--- a/src/cubeb_pulse.c
+++ b/src/cubeb_pulse.c
@@ -280,6 +280,7 @@ trigger_user_callback(pa_stream * s, void const * input_data, size_t nbytes,
if (got < 0) {
WRAP(pa_stream_cancel_write)(s);
stm->shutdown = 1;
+ stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR);
return;
}
// If more iterations move offset of read buffer
@@ -392,6 +393,9 @@ stream_read_callback(pa_stream * s, size_t nbytes, void * u)
if (got < 0 || (size_t)got != read_frames) {
WRAP(pa_stream_cancel_write)(s);
stm->shutdown = 1;
+ if (got < 0) {
+ stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR);
+ }
break;
}
}
diff --git a/src/cubeb_wasapi.cpp b/src/cubeb_wasapi.cpp
index 90e1950..9d5e18f 100644
--- a/src/cubeb_wasapi.cpp
+++ b/src/cubeb_wasapi.cpp
@@ -873,8 +873,11 @@ refill(cubeb_stream * stm, void * input_buffer, long input_frames_count,
long out_frames =
cubeb_resampler_fill(stm->resampler.get(), input_buffer,
&input_frames_count, dest, output_frames_needed);
- /* TODO: Report out_frames < 0 as an error via the API. */
- XASSERT(out_frames >= 0);
+ if (out_frames < 0) {
+ ALOGV("Callback refill error: %d", out_frames);
+ stm->state_callback(stm, stm->user_ptr, CUBEB_STATE_ERROR);
+ return out_frames;
+ }
float volume = 1.0;
{
@@ -1190,6 +1193,7 @@ refill_callback_duplex(cubeb_stream * stm)
static_cast<long>(stm->total_output_frames) - stm->total_input_frames,
static_cast<float>(stm->total_output_frames) / stm->total_input_frames);
+ long got;
if (stm->has_dummy_output) {
ALOGV(
"Duplex callback (dummy output): input frames: %Iu, output frames: %Iu",
@@ -1197,13 +1201,15 @@ refill_callback_duplex(cubeb_stream * stm)
// We don't want to expose the dummy output to the callback so don't pass
// the output buffer (it will be released later with silence in it)
- refill(stm, stm->linear_input_buffer->data(), input_frames, nullptr, 0);
+ got =
+ refill(stm, stm->linear_input_buffer->data(), input_frames, nullptr, 0);
+
} else {
ALOGV("Duplex callback: input frames: %Iu, output frames: %Iu",
input_frames, output_frames);
- refill(stm, stm->linear_input_buffer->data(), input_frames, output_buffer,
- output_frames);
+ got = refill(stm, stm->linear_input_buffer->data(), input_frames,
+ output_buffer, output_frames);
}
stm->linear_input_buffer->clear();
@@ -1219,6 +1225,9 @@ refill_callback_duplex(cubeb_stream * stm)
LOG("failed to release buffer: %lx", hr);
return false;
}
+ if (got < 0) {
+ return false;
+ }
return true;
}
@@ -1245,8 +1254,9 @@ refill_callback_input(cubeb_stream * stm)
long read =
refill(stm, stm->linear_input_buffer->data(), input_frames, nullptr, 0);
-
- XASSERT(read >= 0);
+ if (read < 0) {
+ return false;
+ }
stm->linear_input_buffer->clear();
@@ -1276,8 +1286,9 @@ refill_callback_output(cubeb_stream * stm)
ALOGV("Output callback: output frames requested: %Iu, got %ld", output_frames,
got);
-
- XASSERT(got >= 0);
+ if (got < 0) {
+ return false;
+ }
XASSERT(size_t(got) == output_frames || stm->draining);
hr = stm->render_client->ReleaseBuffer(got, 0);