aboutsummaryrefslogtreecommitdiffhomepage
path: root/src/cubeb_audiounit.cpp
diff options
context:
space:
mode:
authorSteveice10 <[email protected]>2023-12-22 10:49:41 -0800
committerPaul Adenot <[email protected]>2024-01-31 10:51:22 +0100
commitd0ffc6d302b47e2b6c1fc2d38b918b0b1d2b5745 (patch)
tree8fb05285702fa9d2665f329189214b935fd70b55 /src/cubeb_audiounit.cpp
parentdd8a91f98260d2c6171a7cf8a73f8fd4bdbb5337 (diff)
downloadcubeb-d0ffc6d302b47e2b6c1fc2d38b918b0b1d2b5745.tar.gz
cubeb-d0ffc6d302b47e2b6c1fc2d38b918b0b1d2b5745.zip
audiounit: Resample to match output device hardware sample rate in uncommon cases.
In some cases, weird sample rates can cause AudioUnit output units to misbehave. Instead, use resampling for non-native rates to make sure this does not happen.
Diffstat (limited to 'src/cubeb_audiounit.cpp')
-rw-r--r--src/cubeb_audiounit.cpp25
1 files changed, 22 insertions, 3 deletions
diff --git a/src/cubeb_audiounit.cpp b/src/cubeb_audiounit.cpp
index 0341c8d..b32e56f 100644
--- a/src/cubeb_audiounit.cpp
+++ b/src/cubeb_audiounit.cpp
@@ -377,6 +377,14 @@ cubeb_channel_to_channel_label(cubeb_channel channel)
}
}
+bool is_common_sample_rate(Float64 sample_rate)
+{
+ /* Some commonly used sample rates and their multiples and divisors. */
+ return sample_rate == 8000 || sample_rate == 16000 || sample_rate == 22050 ||
+ sample_rate == 32000 || sample_rate == 44100 || sample_rate == 48000 ||
+ sample_rate == 88200 || sample_rate == 96000;
+}
+
#if TARGET_OS_IPHONE
typedef UInt32 AudioDeviceID;
typedef UInt32 AudioObjectID;
@@ -2502,6 +2510,12 @@ audiounit_configure_output(cubeb_stream * stm)
return CUBEB_ERROR;
}
stm->output_hw_rate = output_hw_desc.mSampleRate;
+ if (!is_common_sample_rate(stm->output_desc.mSampleRate)) {
+ /* For uncommon sample rates, we may run into issues with the OS
+ resampler if we don't do the resampling ourselves, so set the
+ AudioUnit sample rate to the hardware rate and resample. */
+ stm->output_desc.mSampleRate = stm->output_hw_rate;
+ }
LOG("(%p) Output device sampling rate: %.2f", stm,
output_hw_desc.mSampleRate);
stm->context->channels = output_hw_desc.mChannelsPerFrame;
@@ -2709,11 +2723,16 @@ audiounit_setup_stream(cubeb_stream * stm)
input_unconverted_params.rate = stm->input_hw_rate;
}
- /* Create resampler. Output params are unchanged
- * because we do not need conversion on the output. */
+ cubeb_stream_params output_unconverted_params;
+ if (has_output(stm)) {
+ output_unconverted_params = stm->output_stream_params;
+ output_unconverted_params.rate = stm->output_desc.mSampleRate;
+ }
+
+ /* Create resampler. */
stm->resampler.reset(cubeb_resampler_create(
stm, has_input(stm) ? &input_unconverted_params : NULL,
- has_output(stm) ? &stm->output_stream_params : NULL, target_sample_rate,
+ has_output(stm) ? &output_unconverted_params : NULL, target_sample_rate,
stm->data_callback, stm->user_ptr, CUBEB_RESAMPLER_QUALITY_DESKTOP,
CUBEB_RESAMPLER_RECLOCK_NONE));
if (!stm->resampler) {