Improve handling of the `DefaultFormatError`

This commit is contained in:
mitchmindtree 2019-06-21 01:34:07 +02:00
parent fbb97f51ef
commit f0e4e312c1
4 changed files with 41 additions and 18 deletions

View File

@ -313,8 +313,7 @@ impl Device {
return Err(DefaultFormatError::StreamTypeNotSupported);
}
Err(SupportedFormatsError::BackendSpecific { err }) => {
unimplemented!();
//return Err(err.into());
return Err(err.into());
}
Ok(fmts) => fmts.collect(),
}

View File

@ -224,18 +224,25 @@ impl Device {
scope: AudioObjectPropertyScope,
) -> Result<Format, DefaultFormatError>
{
fn default_format_error_from_os_status(status: OSStatus) -> Option<DefaultFormatError> {
fn default_format_error_from_os_status(status: OSStatus) -> Result<(), DefaultFormatError> {
let err = match coreaudio::Error::from_os_status(status) {
Err(err) => err,
Ok(_) => return None,
Ok(_) => return Ok(()),
};
match err {
coreaudio::Error::RenderCallbackBufferFormatDoesNotMatchAudioUnitStreamFormat |
coreaudio::Error::NoKnownSubtype |
coreaudio::Error::AudioUnit(coreaudio::error::AudioUnitError::FormatNotSupported) |
coreaudio::Error::AudioCodec(_) |
coreaudio::Error::AudioFormat(_) => Some(DefaultFormatError::StreamTypeNotSupported),
_ => Some(DefaultFormatError::DeviceNotAvailable),
coreaudio::Error::AudioFormat(_) => {
Err(DefaultFormatError::StreamTypeNotSupported)
}
coreaudio::Error::AudioUnit(coreaudio::error::AudioUnitError::NoConnection) => {
Err(DefaultFormatError::DeviceNotAvailable)
}
err => {
let description = format!("{}", std::error::Error::description(&err));
let err = BackendSpecificError { description };
Err(err.into())
}
}
}
@ -256,12 +263,7 @@ impl Device {
&data_size as *const _ as *mut _,
&asbd as *const _ as *mut _,
);
if status != kAudioHardwareNoError as i32 {
let err = default_format_error_from_os_status(status)
.expect("no known error for OSStatus");
return Err(err);
}
default_format_error_from_os_status(status)?;
let sample_format = {
let audio_format = coreaudio::audio_unit::AudioFormat::from_format_and_flag(

View File

@ -347,6 +347,12 @@ pub enum DefaultFormatError {
/// Returned if e.g. the default input format was requested on an output-only audio device.
#[fail(display = "The requested stream type is not supported by the device.")]
StreamTypeNotSupported,
/// See the `BackendSpecificError` docs for more information about this error variant.
#[fail(display = "{}", err)]
BackendSpecific {
#[fail(cause)]
err: BackendSpecificError,
}
}
/// Error that can happen when creating a `Stream`.
@ -765,6 +771,12 @@ impl From<BackendSpecificError> for SupportedFormatsError {
}
}
impl From<BackendSpecificError> for DefaultFormatError {
fn from(err: BackendSpecificError) -> Self {
DefaultFormatError::BackendSpecific { err }
}
}
// If a backend does not provide an API for retrieving supported formats, we query it with a bunch
// of commonly used rates. This is always the case for wasapi and is sometimes the case for alsa.
//

View File

@ -522,9 +522,15 @@ impl Device {
com::com_initialized();
let lock = match self.ensure_future_audio_client() {
Err(ref e) if e.raw_os_error() == Some(AUDCLNT_E_DEVICE_INVALIDATED) =>
return Err(DefaultFormatError::DeviceNotAvailable),
e => e.unwrap(),
Ok(lock) => lock,
Err(ref e) if e.raw_os_error() == Some(AUDCLNT_E_DEVICE_INVALIDATED) => {
return Err(DefaultFormatError::DeviceNotAvailable)
}
Err(e) => {
let description = format!("{}", e);
let err = BackendSpecificError { description };
return Err(err.into());
}
};
let client = lock.unwrap().0;
@ -534,7 +540,11 @@ impl Device {
Err(ref e) if e.raw_os_error() == Some(AUDCLNT_E_DEVICE_INVALIDATED) => {
return Err(DefaultFormatError::DeviceNotAvailable);
},
Err(e) => panic!("{:?}", e),
Err(e) => {
let description = format!("{}", e);
let err = BackendSpecificError { description };
return Err(err.into());
},
Ok(()) => (),
};