cleanup/sync the main loop of *_OpenDevice functions to pick audio format

This commit is contained in:
pionere 2022-01-20 12:18:59 +01:00 committed by Ryan C. Gordon
parent 3939ef72f8
commit 2eafe4340c
18 changed files with 186 additions and 307 deletions

View File

@ -598,10 +598,7 @@ ALSA_OpenDevice(_THIS, void *handle, const char *devname)
} }
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
status = -1; for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
for (test_format = SDL_FirstAudioFormat(this->spec.format);
test_format && (status < 0);) {
status = 0; /* if we can't support a format, it'll become -1. */
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
format = SND_PCM_FORMAT_U8; format = SND_PCM_FORMAT_U8;
@ -634,19 +631,14 @@ ALSA_OpenDevice(_THIS, void *handle, const char *devname)
format = SND_PCM_FORMAT_FLOAT_BE; format = SND_PCM_FORMAT_FLOAT_BE;
break; break;
default: default:
status = -1; continue;
}
if (ALSA_snd_pcm_hw_params_set_format(pcm_handle, hwparams, format) >= 0) {
break; break;
} }
if (status >= 0) {
status = ALSA_snd_pcm_hw_params_set_format(pcm_handle,
hwparams, format);
}
if (status < 0) {
test_format = SDL_NextAudioFormat();
}
} }
if (status < 0) { if (!test_format) {
return SDL_SetError("ALSA: Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "alsa");
} }
this->spec.format = test_format; this->spec.format = test_format;

View File

@ -55,20 +55,18 @@ ANDROIDAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
return SDL_OutOfMemory(); return SDL_OutOfMemory();
} }
test_format = SDL_FirstAudioFormat(this->spec.format); for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
while (test_format != 0) { /* no "UNKNOWN" constant */
if ((test_format == AUDIO_U8) || if ((test_format == AUDIO_U8) ||
(test_format == AUDIO_S16) || (test_format == AUDIO_S16) ||
(test_format == AUDIO_F32)) { (test_format == AUDIO_F32)) {
this->spec.format = test_format; this->spec.format = test_format;
break; break;
} }
test_format = SDL_NextAudioFormat();
} }
if (test_format == 0) { if (!test_format) {
/* Didn't find a compatible format :( */ /* Didn't find a compatible format :( */
return SDL_SetError("No compatible audio format!"); return SDL_SetError("%s: Unsupported audio format", "android");
} }
if (Android_JNI_OpenAudioDevice(iscapture, &this->spec) < 0) { if (Android_JNI_OpenAudioDevice(iscapture, &this->spec) < 0) {

View File

@ -219,8 +219,8 @@ static int
ARTS_OpenDevice(_THIS, void *handle, const char *devname) ARTS_OpenDevice(_THIS, void *handle, const char *devname)
{ {
int rc = 0; int rc = 0;
int bits = 0, frag_spec = 0; int bits, frag_spec = 0;
SDL_AudioFormat test_format = 0, format = 0; SDL_AudioFormat test_format = 0;
/* Initialize all variables that we clean on shutdown */ /* Initialize all variables that we clean on shutdown */
this->hidden = (struct SDL_PrivateAudioData *) this->hidden = (struct SDL_PrivateAudioData *)
@ -231,32 +231,24 @@ ARTS_OpenDevice(_THIS, void *handle, const char *devname)
SDL_zerop(this->hidden); SDL_zerop(this->hidden);
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
for (test_format = SDL_FirstAudioFormat(this->spec.format); for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
!format && test_format;) {
#ifdef DEBUG_AUDIO #ifdef DEBUG_AUDIO
fprintf(stderr, "Trying format 0x%4.4x\n", test_format); fprintf(stderr, "Trying format 0x%4.4x\n", test_format);
#endif #endif
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
bits = 8;
format = 1;
break;
case AUDIO_S16LSB: case AUDIO_S16LSB:
bits = 16;
format = 1;
break; break;
default: default:
format = 0; continue;
break;
}
if (!format) {
test_format = SDL_NextAudioFormat();
} }
break;
} }
if (format == 0) { if (!test_format) {
return SDL_SetError("Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "arts");
} }
this->spec.format = test_format; this->spec.format = test_format;
bits = SDL_AUDIO_BITSIZE(test_format);
if ((rc = SDL_NAME(arts_init) ()) != 0) { if ((rc = SDL_NAME(arts_init) ()) != 0) {
return SDL_SetError("Unable to initialize ARTS: %s", return SDL_SetError("Unable to initialize ARTS: %s",

View File

@ -1018,8 +1018,8 @@ static int
COREAUDIO_OpenDevice(_THIS, void *handle, const char *devname) COREAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
{ {
AudioStreamBasicDescription *strdesc; AudioStreamBasicDescription *strdesc;
SDL_AudioFormat test_format = SDL_FirstAudioFormat(this->spec.format); SDL_AudioFormat test_format;
SDL_bool valid_datatype = SDL_FALSE, iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
SDL_AudioDevice **new_open_devices; SDL_AudioDevice **new_open_devices;
/* Initialize all variables that we clean on shutdown */ /* Initialize all variables that we clean on shutdown */
@ -1076,8 +1076,7 @@ COREAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
strdesc->mSampleRate = this->spec.freq; strdesc->mSampleRate = this->spec.freq;
strdesc->mFramesPerPacket = 1; strdesc->mFramesPerPacket = 1;
while ((!valid_datatype) && (test_format)) { for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
this->spec.format = test_format;
/* CoreAudio handles most of SDL's formats natively, but not U16, apparently. */ /* CoreAudio handles most of SDL's formats natively, but not U16, apparently. */
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
@ -1088,26 +1087,26 @@ COREAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
case AUDIO_S32MSB: case AUDIO_S32MSB:
case AUDIO_F32LSB: case AUDIO_F32LSB:
case AUDIO_F32MSB: case AUDIO_F32MSB:
valid_datatype = SDL_TRUE;
strdesc->mBitsPerChannel = SDL_AUDIO_BITSIZE(this->spec.format);
if (SDL_AUDIO_ISBIGENDIAN(this->spec.format))
strdesc->mFormatFlags |= kLinearPCMFormatFlagIsBigEndian;
if (SDL_AUDIO_ISFLOAT(this->spec.format))
strdesc->mFormatFlags |= kLinearPCMFormatFlagIsFloat;
else if (SDL_AUDIO_ISSIGNED(this->spec.format))
strdesc->mFormatFlags |= kLinearPCMFormatFlagIsSignedInteger;
break; break;
default: default:
test_format = SDL_NextAudioFormat(); continue;
break;
} }
break;
} }
if (!valid_datatype) { /* shouldn't happen, but just in case... */ if (!test_format) { /* shouldn't happen, but just in case... */
return SDL_SetError("Unsupported audio format"); return SDL_SetError("Unsupported audio format");
} }
this->spec.format = test_format;
strdesc->mBitsPerChannel = SDL_AUDIO_BITSIZE(test_format);
if (SDL_AUDIO_ISBIGENDIAN(test_format))
strdesc->mFormatFlags |= kLinearPCMFormatFlagIsBigEndian;
if (SDL_AUDIO_ISFLOAT(test_format))
strdesc->mFormatFlags |= kLinearPCMFormatFlagIsFloat;
else if (SDL_AUDIO_ISSIGNED(test_format))
strdesc->mFormatFlags |= kLinearPCMFormatFlagIsSignedInteger;
strdesc->mBytesPerFrame = strdesc->mChannelsPerFrame * strdesc->mBitsPerChannel / 8; strdesc->mBytesPerFrame = strdesc->mChannelsPerFrame * strdesc->mBitsPerChannel / 8;
strdesc->mBytesPerPacket = strdesc->mBytesPerFrame * strdesc->mFramesPerPacket; strdesc->mBytesPerPacket = strdesc->mBytesPerFrame * strdesc->mFramesPerPacket;

View File

@ -477,10 +477,9 @@ DSOUND_OpenDevice(_THIS, void *handle, const char *devname)
{ {
const DWORD numchunks = 8; const DWORD numchunks = 8;
HRESULT result; HRESULT result;
SDL_bool valid_format = SDL_FALSE;
SDL_bool tried_format = SDL_FALSE; SDL_bool tried_format = SDL_FALSE;
SDL_bool iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
SDL_AudioFormat test_format = SDL_FirstAudioFormat(this->spec.format); SDL_AudioFormat test_format;
LPGUID guid = (LPGUID) handle; LPGUID guid = (LPGUID) handle;
DWORD bufsize; DWORD bufsize;
@ -511,7 +510,7 @@ DSOUND_OpenDevice(_THIS, void *handle, const char *devname)
} }
} }
while ((!valid_format) && (test_format)) { for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
case AUDIO_S16: case AUDIO_S16:
@ -548,19 +547,21 @@ DSOUND_OpenDevice(_THIS, void *handle, const char *devname)
rc = iscapture ? CreateCaptureBuffer(this, bufsize, &wfmt) : CreateSecondary(this, bufsize, &wfmt); rc = iscapture ? CreateCaptureBuffer(this, bufsize, &wfmt) : CreateSecondary(this, bufsize, &wfmt);
if (rc == 0) { if (rc == 0) {
this->hidden->num_buffers = numchunks; this->hidden->num_buffers = numchunks;
valid_format = SDL_TRUE; break;
} }
} }
break; continue;
default:
continue;
} }
test_format = SDL_NextAudioFormat(); break;
} }
if (!valid_format) { if (!test_format) {
if (tried_format) { if (tried_format) {
return -1; /* CreateSecondary() should have called SDL_SetError(). */ return -1; /* CreateSecondary() should have called SDL_SetError(). */
} }
return SDL_SetError("DirectSound: Unsupported audio format"); return SDL_SetError("%s: Unsupported audio format", "directsound");
} }
/* Playback buffers will auto-start playing in DSOUND_WaitDevice() */ /* Playback buffers will auto-start playing in DSOUND_WaitDevice() */

View File

@ -194,7 +194,6 @@ EMSCRIPTENAUDIO_CloseDevice(_THIS)
static int static int
EMSCRIPTENAUDIO_OpenDevice(_THIS, void *handle, const char *devname) EMSCRIPTENAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
{ {
SDL_bool valid_format = SDL_FALSE;
SDL_AudioFormat test_format; SDL_AudioFormat test_format;
SDL_bool iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
int result; int result;
@ -229,22 +228,21 @@ EMSCRIPTENAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
return SDL_SetError("Web Audio API is not available!"); return SDL_SetError("Web Audio API is not available!");
} }
test_format = SDL_FirstAudioFormat(this->spec.format); for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
while ((!valid_format) && (test_format)) {
switch (test_format) { switch (test_format) {
case AUDIO_F32: /* web audio only supports floats */ case AUDIO_F32: /* web audio only supports floats */
this->spec.format = test_format;
valid_format = SDL_TRUE;
break; break;
default:
continue;
} }
test_format = SDL_NextAudioFormat(); break;
} }
if (!valid_format) { if (!test_format) {
/* Didn't find a compatible format :( */ /* Didn't find a compatible format :( */
return SDL_SetError("No compatible audio format!"); return SDL_SetError("%s: Unsupported audio format", "emscripten");
} }
this->spec.format = test_format;
/* Initialize all variables that we clean on shutdown */ /* Initialize all variables that we clean on shutdown */
#if 0 /* !!! FIXME: currently not used. Can we move some stuff off the SDL2 namespace? --ryan. */ #if 0 /* !!! FIXME: currently not used. Can we move some stuff off the SDL2 namespace? --ryan. */

View File

@ -177,7 +177,7 @@ static int
SDL_FS_OpenDevice(_THIS, void *handle, const char *devname) SDL_FS_OpenDevice(_THIS, void *handle, const char *devname)
{ {
int bytes; int bytes;
SDL_AudioFormat test_format = 0, format = 0; SDL_AudioFormat test_format;
FSSampleFormat fs_format; FSSampleFormat fs_format;
FSStreamDescription desc; FSStreamDescription desc;
DirectResult ret; DirectResult ret;
@ -191,45 +191,34 @@ SDL_FS_OpenDevice(_THIS, void *handle, const char *devname)
SDL_zerop(this->hidden); SDL_zerop(this->hidden);
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
for (test_format = SDL_FirstAudioFormat(this->spec.format); for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
!format && test_format;) {
#ifdef DEBUG_AUDIO #ifdef DEBUG_AUDIO
fprintf(stderr, "Trying format 0x%4.4x\n", test_format); fprintf(stderr, "Trying format 0x%4.4x\n", test_format);
#endif #endif
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
fs_format = FSSF_U8; fs_format = FSSF_U8;
bytes = 1;
format = 1;
break; break;
case AUDIO_S16SYS: case AUDIO_S16SYS:
fs_format = FSSF_S16; fs_format = FSSF_S16;
bytes = 2;
format = 1;
break; break;
case AUDIO_S32SYS: case AUDIO_S32SYS:
fs_format = FSSF_S32; fs_format = FSSF_S32;
bytes = 4;
format = 1;
break; break;
case AUDIO_F32SYS: case AUDIO_F32SYS:
fs_format = FSSF_FLOAT; fs_format = FSSF_FLOAT;
bytes = 4;
format = 1;
break; break;
default: default:
format = 0; continue;
break;
}
if (!format) {
test_format = SDL_NextAudioFormat();
} }
break;
} }
if (format == 0) { if (!test_format) {
return SDL_SetError("Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "fusionsound");
} }
this->spec.format = test_format; this->spec.format = test_format;
bytes = SDL_AUDIO_BITSIZE(test_format) / 8;
/* Retrieve the main sound interface. */ /* Retrieve the main sound interface. */
ret = SDL_NAME(FusionSoundCreate) (&this->hidden->fs); ret = SDL_NAME(FusionSoundCreate) (&this->hidden->fs);

View File

@ -122,9 +122,8 @@ UnmaskSignals(sigset_t * omask)
static int static int
HAIKUAUDIO_OpenDevice(_THIS, void *handle, const char *devname) HAIKUAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
{ {
int valid_datatype = 0;
media_raw_audio_format format; media_raw_audio_format format;
SDL_AudioFormat test_format = SDL_FirstAudioFormat(_this->spec.format); SDL_AudioFormat test_format;
/* Initialize all variables that we clean on shutdown */ /* Initialize all variables that we clean on shutdown */
_this->hidden = new SDL_PrivateAudioData; _this->hidden = new SDL_PrivateAudioData;
@ -138,9 +137,7 @@ HAIKUAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
format.byte_order = B_MEDIA_LITTLE_ENDIAN; format.byte_order = B_MEDIA_LITTLE_ENDIAN;
format.frame_rate = (float) _this->spec.freq; format.frame_rate = (float) _this->spec.freq;
format.channel_count = _this->spec.channels; /* !!! FIXME: support > 2? */ format.channel_count = _this->spec.channels; /* !!! FIXME: support > 2? */
while ((!valid_datatype) && (test_format)) { for (test_format = SDL_FirstAudioFormat(_this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
valid_datatype = 1;
_this->spec.format = test_format;
switch (test_format) { switch (test_format) {
case AUDIO_S8: case AUDIO_S8:
format.format = media_raw_audio_format::B_AUDIO_CHAR; format.format = media_raw_audio_format::B_AUDIO_CHAR;
@ -178,15 +175,15 @@ HAIKUAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
break; break;
default: default:
valid_datatype = 0; continue;
test_format = SDL_NextAudioFormat();
break;
} }
break;
} }
if (!valid_datatype) { /* shouldn't happen, but just in case... */ if (!test_format) { /* shouldn't happen, but just in case... */
return SDL_SetError("Unsupported audio format"); return SDL_SetError("%s: Unsupported audio format", "haiku");
} }
_this->spec.format = test_format;
/* Calculate the final parameters for this audio specification */ /* Calculate the final parameters for this audio specification */
SDL_CalculateAudioSpec(&_this->spec); SDL_CalculateAudioSpec(&_this->spec);

View File

@ -237,26 +237,6 @@ NAS_CloseDevice(_THIS)
SDL_free(this->hidden); SDL_free(this->hidden);
} }
static unsigned char
sdlformat_to_auformat(unsigned int fmt)
{
switch (fmt) {
case AUDIO_U8:
return AuFormatLinearUnsigned8;
case AUDIO_S8:
return AuFormatLinearSigned8;
case AUDIO_U16LSB:
return AuFormatLinearUnsigned16LSB;
case AUDIO_U16MSB:
return AuFormatLinearUnsigned16MSB;
case AUDIO_S16LSB:
return AuFormatLinearSigned16LSB;
case AUDIO_S16MSB:
return AuFormatLinearSigned16MSB;
}
return AuNone;
}
static AuBool static AuBool
event_handler(AuServer * aud, AuEvent * ev, AuEventHandlerRec * hnd) event_handler(AuServer * aud, AuEvent * ev, AuEventHandlerRec * hnd)
{ {
@ -336,7 +316,7 @@ NAS_OpenDevice(_THIS, void *handle, const char *devname)
AuElement elms[3]; AuElement elms[3];
int buffer_size; int buffer_size;
SDL_bool iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
SDL_AudioFormat test_format, format; SDL_AudioFormat test_format, format = 0;
/* Initialize all variables that we clean on shutdown */ /* Initialize all variables that we clean on shutdown */
this->hidden = (struct SDL_PrivateAudioData *) this->hidden = (struct SDL_PrivateAudioData *)
@ -347,16 +327,33 @@ NAS_OpenDevice(_THIS, void *handle, const char *devname)
SDL_zerop(this->hidden); SDL_zerop(this->hidden);
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
format = 0; for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
for (test_format = SDL_FirstAudioFormat(this->spec.format); switch (test_format) {
!format && test_format;) { case AUDIO_U8:
format = sdlformat_to_auformat(test_format); format = AuFormatLinearUnsigned8;
if (format == AuNone) { break;
test_format = SDL_NextAudioFormat(); case AUDIO_S8:
format = AuFormatLinearSigned8;
break;
case AUDIO_U16LSB:
format = AuFormatLinearUnsigned16LSB;
break;
case AUDIO_U16MSB:
format = AuFormatLinearUnsigned16MSB;
break;
case AUDIO_S16LSB:
format = AuFormatLinearSigned16LSB;
break;
case AUDIO_S16MSB:
format = AuFormatLinearSigned16MSB;
break;
default:
continue;
} }
break;
} }
if (format == 0) { if (!test_format) {
return SDL_SetError("NAS: Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "nas");
} }
this->spec.format = test_format; this->spec.format = test_format;

View File

@ -205,7 +205,8 @@ static int
NETBSDAUDIO_OpenDevice(_THIS, void *handle, const char *devname) NETBSDAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
{ {
SDL_bool iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
SDL_AudioFormat format = 0; SDL_AudioFormat test_format;
int encoding = AUDIO_ENCODING_NONE;
audio_info_t info, hwinfo; audio_info_t info, hwinfo;
struct audio_prinfo *prinfo = iscapture ? &info.record : &info.play; struct audio_prinfo *prinfo = iscapture ? &info.record : &info.play;
@ -245,54 +246,46 @@ NETBSDAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
} }
#endif #endif
prinfo->encoding = AUDIO_ENCODING_NONE;
prinfo->sample_rate = this->spec.freq; prinfo->sample_rate = this->spec.freq;
prinfo->channels = this->spec.channels; prinfo->channels = this->spec.channels;
for (format = SDL_FirstAudioFormat(this->spec.format); format;) { for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
switch (format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
prinfo->encoding = AUDIO_ENCODING_ULINEAR; encoding = AUDIO_ENCODING_ULINEAR;
prinfo->precision = 8;
break; break;
case AUDIO_S8: case AUDIO_S8:
prinfo->encoding = AUDIO_ENCODING_SLINEAR; encoding = AUDIO_ENCODING_SLINEAR;
prinfo->precision = 8;
break; break;
case AUDIO_S16LSB: case AUDIO_S16LSB:
prinfo->encoding = AUDIO_ENCODING_SLINEAR_LE; encoding = AUDIO_ENCODING_SLINEAR_LE;
prinfo->precision = 16;
break; break;
case AUDIO_S16MSB: case AUDIO_S16MSB:
prinfo->encoding = AUDIO_ENCODING_SLINEAR_BE; encoding = AUDIO_ENCODING_SLINEAR_BE;
prinfo->precision = 16;
break; break;
case AUDIO_U16LSB: case AUDIO_U16LSB:
prinfo->encoding = AUDIO_ENCODING_ULINEAR_LE; encoding = AUDIO_ENCODING_ULINEAR_LE;
prinfo->precision = 16;
break; break;
case AUDIO_U16MSB: case AUDIO_U16MSB:
prinfo->encoding = AUDIO_ENCODING_ULINEAR_BE; encoding = AUDIO_ENCODING_ULINEAR_BE;
prinfo->precision = 16;
break; break;
case AUDIO_S32LSB: case AUDIO_S32LSB:
prinfo->encoding = AUDIO_ENCODING_SLINEAR_LE; encoding = AUDIO_ENCODING_SLINEAR_LE;
prinfo->precision = 32;
break; break;
case AUDIO_S32MSB: case AUDIO_S32MSB:
prinfo->encoding = AUDIO_ENCODING_SLINEAR_BE; encoding = AUDIO_ENCODING_SLINEAR_BE;
prinfo->precision = 32;
break; break;
default:
continue;
} }
if (prinfo->encoding != AUDIO_ENCODING_NONE) { break;
break;
}
format = SDL_NextAudioFormat();
} }
if (prinfo->encoding == AUDIO_ENCODING_NONE) { if (!test_format) {
return SDL_SetError("No supported encoding for 0x%x", this->spec.format); return SDL_SetError("%s: Unsupported audio format", "netbsd");
} }
prinfo->encoding = encoding;
prinfo->precision = SDL_AUDIO_BITSIZE(test_format);
info.hiwat = 5; info.hiwat = 5;
info.lowat = 3; info.lowat = 3;
@ -305,7 +298,7 @@ NETBSDAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
} }
/* Final spec used for the device. */ /* Final spec used for the device. */
this->spec.format = format; this->spec.format = test_format;
this->spec.freq = prinfo->sample_rate; this->spec.freq = prinfo->sample_rate;
this->spec.channels = prinfo->channels; this->spec.channels = prinfo->channels;

View File

@ -418,15 +418,14 @@ openslES_CreatePCMPlayer(_THIS)
/* Just go with signed 16-bit audio as it's the most compatible */ /* Just go with signed 16-bit audio as it's the most compatible */
this->spec.format = AUDIO_S16SYS; this->spec.format = AUDIO_S16SYS;
#else #else
SDL_AudioFormat test_format = SDL_FirstAudioFormat(this->spec.format); SDL_AudioFormat test_format;
while (test_format != 0) { for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
if (SDL_AUDIO_ISSIGNED(test_format) && SDL_AUDIO_ISINT(test_format)) { if (SDL_AUDIO_ISSIGNED(test_format) && SDL_AUDIO_ISINT(test_format)) {
break; break;
} }
test_format = SDL_NextAudioFormat();
} }
if (test_format == 0) { if (!test_format) {
/* Didn't find a compatible format : */ /* Didn't find a compatible format : */
LOGI( "No compatible audio format, using signed 16-bit audio" ); LOGI( "No compatible audio format, using signed 16-bit audio" );
test_format = AUDIO_S16SYS; test_format = AUDIO_S16SYS;

View File

@ -251,7 +251,7 @@ static void OS2_CloseDevice(_THIS)
static int OS2_OpenDevice(_THIS, void *handle, const char *devname) static int OS2_OpenDevice(_THIS, void *handle, const char *devname)
{ {
SDL_PrivateAudioData *pAData; SDL_PrivateAudioData *pAData;
SDL_AudioFormat SDLAudioFmt; SDL_AudioFormat test_format;
MCI_AMP_OPEN_PARMS stMCIAmpOpen; MCI_AMP_OPEN_PARMS stMCIAmpOpen;
MCI_BUFFER_PARMS stMCIBuffer; MCI_BUFFER_PARMS stMCIBuffer;
ULONG ulRC; ULONG ulRC;
@ -263,14 +263,13 @@ static int OS2_OpenDevice(_THIS, void *handle, const char *devname)
SDL_zero(stMCIAmpOpen); SDL_zero(stMCIAmpOpen);
SDL_zero(stMCIBuffer); SDL_zero(stMCIBuffer);
for (SDLAudioFmt = SDL_FirstAudioFormat(_this->spec.format); for (test_format = SDL_FirstAudioFormat(_this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
SDLAudioFmt != 0; SDLAudioFmt = SDL_NextAudioFormat()) { if (test_format == AUDIO_U8 || test_format == AUDIO_S16)
if (SDLAudioFmt == AUDIO_U8 || SDLAudioFmt == AUDIO_S16)
break; break;
} }
if (SDLAudioFmt == 0) { if (!test_format) {
debug_os2("Unsupported audio format, AUDIO_S16 used"); debug_os2("Unsupported audio format, AUDIO_S16 used");
SDLAudioFmt = AUDIO_S16; test_format = AUDIO_S16;
} }
pAData = (SDL_PrivateAudioData *) SDL_calloc(1, sizeof(struct SDL_PrivateAudioData)); pAData = (SDL_PrivateAudioData *) SDL_calloc(1, sizeof(struct SDL_PrivateAudioData));
@ -330,7 +329,7 @@ static int OS2_OpenDevice(_THIS, void *handle, const char *devname)
&stMCIAmpSet, 0); &stMCIAmpSet, 0);
} }
_this->spec.format = SDLAudioFmt; _this->spec.format = test_format;
_this->spec.channels = _this->spec.channels > 1 ? 2 : 1; _this->spec.channels = _this->spec.channels > 1 ? 2 : 1;
if (_this->spec.freq < 8000) { if (_this->spec.freq < 8000) {
_this->spec.freq = 8000; _this->spec.freq = 8000;
@ -342,7 +341,7 @@ static int OS2_OpenDevice(_THIS, void *handle, const char *devname)
/* Setup mixer. */ /* Setup mixer. */
pAData->stMCIMixSetup.ulFormatTag = MCI_WAVE_FORMAT_PCM; pAData->stMCIMixSetup.ulFormatTag = MCI_WAVE_FORMAT_PCM;
pAData->stMCIMixSetup.ulBitsPerSample = SDL_AUDIO_BITSIZE(SDLAudioFmt); pAData->stMCIMixSetup.ulBitsPerSample = SDL_AUDIO_BITSIZE(test_format);
pAData->stMCIMixSetup.ulSamplesPerSec = _this->spec.freq; pAData->stMCIMixSetup.ulSamplesPerSec = _this->spec.freq;
pAData->stMCIMixSetup.ulChannels = _this->spec.channels; pAData->stMCIMixSetup.ulChannels = _this->spec.channels;
pAData->stMCIMixSetup.ulDeviceType = MCI_DEVTYPE_WAVEFORM_AUDIO; pAData->stMCIMixSetup.ulDeviceType = MCI_DEVTYPE_WAVEFORM_AUDIO;

View File

@ -228,7 +228,7 @@ PAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
const char *workaround = SDL_getenv("SDL_DSP_NOSELECT"); const char *workaround = SDL_getenv("SDL_DSP_NOSELECT");
char audiodev[1024]; char audiodev[1024];
const char *err = NULL; const char *err = NULL;
int format; int flags;
int bytes_per_sample; int bytes_per_sample;
SDL_AudioFormat test_format; SDL_AudioFormat test_format;
audio_init paud_init; audio_init paud_init;
@ -316,63 +316,44 @@ PAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
paud_init.channels = this->spec.channels; paud_init.channels = this->spec.channels;
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
format = 0; for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
for (test_format = SDL_FirstAudioFormat(this->spec.format);
!format && test_format;) {
#ifdef DEBUG_AUDIO #ifdef DEBUG_AUDIO
fprintf(stderr, "Trying format 0x%4.4x\n", test_format); fprintf(stderr, "Trying format 0x%4.4x\n", test_format);
#endif #endif
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
bytes_per_sample = 1; flags = TWOS_COMPLEMENT | FIXED;
paud_init.bits_per_sample = 8;
paud_init.flags = TWOS_COMPLEMENT | FIXED;
format = 1;
break; break;
case AUDIO_S8: case AUDIO_S8:
bytes_per_sample = 1; flags = SIGNED | TWOS_COMPLEMENT | FIXED;
paud_init.bits_per_sample = 8;
paud_init.flags = SIGNED | TWOS_COMPLEMENT | FIXED;
format = 1;
break; break;
case AUDIO_S16LSB: case AUDIO_S16LSB:
bytes_per_sample = 2; flags = SIGNED | TWOS_COMPLEMENT | FIXED;
paud_init.bits_per_sample = 16;
paud_init.flags = SIGNED | TWOS_COMPLEMENT | FIXED;
format = 1;
break; break;
case AUDIO_S16MSB: case AUDIO_S16MSB:
bytes_per_sample = 2; flags = BIG_ENDIAN | SIGNED | TWOS_COMPLEMENT | FIXED;
paud_init.bits_per_sample = 16;
paud_init.flags = BIG_ENDIAN | SIGNED | TWOS_COMPLEMENT | FIXED;
format = 1;
break; break;
case AUDIO_U16LSB: case AUDIO_U16LSB:
bytes_per_sample = 2; flags = TWOS_COMPLEMENT | FIXED;
paud_init.bits_per_sample = 16;
paud_init.flags = TWOS_COMPLEMENT | FIXED;
format = 1;
break; break;
case AUDIO_U16MSB: case AUDIO_U16MSB:
bytes_per_sample = 2; flags = BIG_ENDIAN | TWOS_COMPLEMENT | FIXED;
paud_init.bits_per_sample = 16;
paud_init.flags = BIG_ENDIAN | TWOS_COMPLEMENT | FIXED;
format = 1;
break; break;
default: default:
break; continue;
}
if (!format) {
test_format = SDL_NextAudioFormat();
} }
break;
} }
if (format == 0) { if (!test_format) {
#ifdef DEBUG_AUDIO #ifdef DEBUG_AUDIO
fprintf(stderr, "Couldn't find any hardware audio formats\n"); fprintf(stderr, "Couldn't find any hardware audio formats\n");
#endif #endif
return SDL_SetError("Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "paud");
} }
this->spec.format = test_format; this->spec.format = test_format;
paud_init.bits_per_sample = SDL_AUDIO_BITSIZE(test_format);
bytes_per_sample = SDL_AUDIO_BITSIZE(test_format) / 8;
paud_init.flags = flags;
/* /*
* We know the buffer size and the max number of subsequent writes * We know the buffer size and the max number of subsequent writes
@ -406,28 +387,25 @@ PAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
if (ioctl(fd, AUDIO_INIT, &paud_init) < 0) { if (ioctl(fd, AUDIO_INIT, &paud_init) < 0) {
switch (paud_init.rc) { switch (paud_init.rc) {
case 1: case 1:
err = "Couldn't set audio format: DSP can't do play requests"; err = "DSP can't do play requests";
break; break;
case 2: case 2:
err = "Couldn't set audio format: DSP can't do record requests"; err = "DSP can't do record requests";
break; break;
case 4: case 4:
err = "Couldn't set audio format: request was invalid"; err = "request was invalid";
break; break;
case 5: case 5:
err = "Couldn't set audio format: conflict with open's flags"; err = "conflict with open's flags";
break; break;
case 6: case 6:
err = "Couldn't set audio format: out of DSP MIPS or memory"; err = "out of DSP MIPS or memory";
break; break;
default: default:
err = "Couldn't set audio format: not documented in sys/audio.h"; err = "not documented in sys/audio.h";
break; break;
} }
} return SDL_SetError("paud: Couldn't set audio format (%s)", err);
if (err != NULL) {
return SDL_SetError("Paudio: %s", err);
} }
/* Allocate mixing buffer */ /* Allocate mixing buffer */

View File

@ -547,14 +547,14 @@ static int
PULSEAUDIO_OpenDevice(_THIS, void *handle, const char *devname) PULSEAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
{ {
struct SDL_PrivateAudioData *h = NULL; struct SDL_PrivateAudioData *h = NULL;
Uint16 test_format = 0; SDL_AudioFormat test_format;
pa_sample_spec paspec; pa_sample_spec paspec;
pa_buffer_attr paattr; pa_buffer_attr paattr;
pa_channel_map pacmap; pa_channel_map pacmap;
pa_stream_flags_t flags = 0; pa_stream_flags_t flags = 0;
const char *name = NULL; const char *name = NULL;
SDL_bool iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
int state = 0; int state = 0, format = PA_SAMPLE_INVALID;
int rc = 0; int rc = 0;
/* Initialize all variables that we clean on shutdown */ /* Initialize all variables that we clean on shutdown */
@ -565,48 +565,43 @@ PULSEAUDIO_OpenDevice(_THIS, void *handle, const char *devname)
} }
SDL_zerop(this->hidden); SDL_zerop(this->hidden);
paspec.format = PA_SAMPLE_INVALID;
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
for (test_format = SDL_FirstAudioFormat(this->spec.format); for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
(paspec.format == PA_SAMPLE_INVALID) && test_format;) {
#ifdef DEBUG_AUDIO #ifdef DEBUG_AUDIO
fprintf(stderr, "Trying format 0x%4.4x\n", test_format); fprintf(stderr, "Trying format 0x%4.4x\n", test_format);
#endif #endif
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
paspec.format = PA_SAMPLE_U8; format = PA_SAMPLE_U8;
break; break;
case AUDIO_S16LSB: case AUDIO_S16LSB:
paspec.format = PA_SAMPLE_S16LE; format = PA_SAMPLE_S16LE;
break; break;
case AUDIO_S16MSB: case AUDIO_S16MSB:
paspec.format = PA_SAMPLE_S16BE; format = PA_SAMPLE_S16BE;
break; break;
case AUDIO_S32LSB: case AUDIO_S32LSB:
paspec.format = PA_SAMPLE_S32LE; format = PA_SAMPLE_S32LE;
break; break;
case AUDIO_S32MSB: case AUDIO_S32MSB:
paspec.format = PA_SAMPLE_S32BE; format = PA_SAMPLE_S32BE;
break; break;
case AUDIO_F32LSB: case AUDIO_F32LSB:
paspec.format = PA_SAMPLE_FLOAT32LE; format = PA_SAMPLE_FLOAT32LE;
break; break;
case AUDIO_F32MSB: case AUDIO_F32MSB:
paspec.format = PA_SAMPLE_FLOAT32BE; format = PA_SAMPLE_FLOAT32BE;
break; break;
default: default:
paspec.format = PA_SAMPLE_INVALID; continue;
break;
}
if (paspec.format == PA_SAMPLE_INVALID) {
test_format = SDL_NextAudioFormat();
} }
break;
} }
if (paspec.format == PA_SAMPLE_INVALID) { if (!test_format) {
return SDL_SetError("Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "pulseaudio");
} }
this->spec.format = test_format; this->spec.format = test_format;
paspec.format = format;
/* Calculate the final parameters for this audio specification */ /* Calculate the final parameters for this audio specification */
#ifdef PA_STREAM_ADJUST_LATENCY #ifdef PA_STREAM_ADJUST_LATENCY

View File

@ -263,8 +263,7 @@ QSA_OpenDevice(_THIS, void *handle, const char *devname)
SDL_Bool iscapture = this->iscapture; SDL_Bool iscapture = this->iscapture;
int status = 0; int status = 0;
int format = 0; int format = 0;
SDL_AudioFormat test_format = 0; SDL_AudioFormat test_format;
int found = 0;
snd_pcm_channel_setup_t csetup; snd_pcm_channel_setup_t csetup;
snd_pcm_channel_params_t cparams; snd_pcm_channel_params_t cparams;
@ -303,89 +302,49 @@ QSA_OpenDevice(_THIS, void *handle, const char *devname)
} }
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
format = 0; for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
/* can't use format as SND_PCM_SFMT_U8 = 0 in qsa */
found = 0;
for (test_format = SDL_FirstAudioFormat(this->spec.format); !found;) {
/* if match found set format to equivalent QSA format */ /* if match found set format to equivalent QSA format */
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
{ format = SND_PCM_SFMT_U8;
format = SND_PCM_SFMT_U8;
found = 1;
}
break; break;
case AUDIO_S8: case AUDIO_S8:
{ format = SND_PCM_SFMT_S8;
format = SND_PCM_SFMT_S8;
found = 1;
}
break; break;
case AUDIO_S16LSB: case AUDIO_S16LSB:
{ format = SND_PCM_SFMT_S16_LE;
format = SND_PCM_SFMT_S16_LE;
found = 1;
}
break; break;
case AUDIO_S16MSB: case AUDIO_S16MSB:
{ format = SND_PCM_SFMT_S16_BE;
format = SND_PCM_SFMT_S16_BE;
found = 1;
}
break; break;
case AUDIO_U16LSB: case AUDIO_U16LSB:
{ format = SND_PCM_SFMT_U16_LE;
format = SND_PCM_SFMT_U16_LE;
found = 1;
}
break; break;
case AUDIO_U16MSB: case AUDIO_U16MSB:
{ format = SND_PCM_SFMT_U16_BE;
format = SND_PCM_SFMT_U16_BE;
found = 1;
}
break; break;
case AUDIO_S32LSB: case AUDIO_S32LSB:
{ format = SND_PCM_SFMT_S32_LE;
format = SND_PCM_SFMT_S32_LE;
found = 1;
}
break; break;
case AUDIO_S32MSB: case AUDIO_S32MSB:
{ format = SND_PCM_SFMT_S32_BE;
format = SND_PCM_SFMT_S32_BE;
found = 1;
}
break; break;
case AUDIO_F32LSB: case AUDIO_F32LSB:
{ format = SND_PCM_SFMT_FLOAT_LE;
format = SND_PCM_SFMT_FLOAT_LE;
found = 1;
}
break; break;
case AUDIO_F32MSB: case AUDIO_F32MSB:
{ format = SND_PCM_SFMT_FLOAT_BE;
format = SND_PCM_SFMT_FLOAT_BE;
found = 1;
}
break; break;
default: default:
{ continue;
break;
}
}
if (!found) {
test_format = SDL_NextAudioFormat();
} }
break;
} }
/* assumes test_format not 0 on success */ /* assumes test_format not 0 on success */
if (test_format == 0) { /* can't use format as SND_PCM_SFMT_U8 = 0 in qsa */
return SDL_SetError("QSA: Couldn't find any hardware audio formats"); if (!test_format) {
return SDL_SetError("%s: Unsupported audio format", "qsa");
} }
this->spec.format = test_format; this->spec.format = test_format;
/* Set the audio format */ /* Set the audio format */

View File

@ -239,10 +239,9 @@ SNDIO_CloseDevice(_THIS)
static int static int
SNDIO_OpenDevice(_THIS, void *handle, const char *devname) SNDIO_OpenDevice(_THIS, void *handle, const char *devname)
{ {
SDL_AudioFormat test_format = SDL_FirstAudioFormat(this->spec.format); SDL_AudioFormat test_format;
struct sio_par par; struct sio_par par;
SDL_bool iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
int status;
this->hidden = (struct SDL_PrivateAudioData *) this->hidden = (struct SDL_PrivateAudioData *)
SDL_malloc(sizeof(*this->hidden)); SDL_malloc(sizeof(*this->hidden));
@ -274,8 +273,7 @@ SNDIO_OpenDevice(_THIS, void *handle, const char *devname)
par.appbufsz = par.round * 2; par.appbufsz = par.round * 2;
/* Try for a closest match on audio format */ /* Try for a closest match on audio format */
status = -1; for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
while (test_format && (status < 0)) {
if (!SDL_AUDIO_ISFLOAT(test_format)) { if (!SDL_AUDIO_ISFLOAT(test_format)) {
par.le = SDL_AUDIO_ISLITTLEENDIAN(test_format) ? 1 : 0; par.le = SDL_AUDIO_ISLITTLEENDIAN(test_format) ? 1 : 0;
par.sig = SDL_AUDIO_ISSIGNED(test_format) ? 1 : 0; par.sig = SDL_AUDIO_ISSIGNED(test_format) ? 1 : 0;
@ -291,15 +289,13 @@ SNDIO_OpenDevice(_THIS, void *handle, const char *devname)
continue; continue;
} }
if ((par.bits == 8 * par.bps) || (par.msb)) { if ((par.bits == 8 * par.bps) || (par.msb)) {
status = 0;
break; break;
} }
} }
test_format = SDL_NextAudioFormat();
} }
if (status < 0) { if (!test_format) {
return SDL_SetError("sndio: Couldn't find any hardware audio formats"); return SDL_SetError("%s: Unsupported audio format", "sndio");
} }
if ((par.bps == 4) && (par.sig) && (par.le)) if ((par.bps == 4) && (par.sig) && (par.le))

View File

@ -550,7 +550,7 @@ WASAPI_PrepDevice(_THIS, const SDL_bool updatestream)
} }
if (!test_format) { if (!test_format) {
return SDL_SetError("WASAPI: Unsupported audio format"); return SDL_SetError("%s: Unsupported audio format", "wasapi");
} }
ret = IAudioClient_GetDevicePeriod(client, &default_period, NULL); ret = IAudioClient_GetDevicePeriod(client, &default_period, NULL);

View File

@ -285,8 +285,8 @@ PrepWaveFormat(_THIS, UINT devId, WAVEFORMATEX *pfmt, const int iscapture)
static int static int
WINMM_OpenDevice(_THIS, void *handle, const char *devname) WINMM_OpenDevice(_THIS, void *handle, const char *devname)
{ {
SDL_AudioFormat test_format = SDL_FirstAudioFormat(this->spec.format); SDL_AudioFormat test_format;
SDL_bool valid_datatype = SDL_FALSE, iscapture = this->iscapture; SDL_bool iscapture = this->iscapture;
MMRESULT result; MMRESULT result;
WAVEFORMATEX waveformat; WAVEFORMATEX waveformat;
UINT devId = WAVE_MAPPER; /* WAVE_MAPPER == choose system's default */ UINT devId = WAVE_MAPPER; /* WAVE_MAPPER == choose system's default */
@ -313,7 +313,7 @@ WINMM_OpenDevice(_THIS, void *handle, const char *devname)
if (this->spec.channels > 2) if (this->spec.channels > 2)
this->spec.channels = 2; /* !!! FIXME: is this right? */ this->spec.channels = 2; /* !!! FIXME: is this right? */
while ((!valid_datatype) && (test_format)) { for (test_format = SDL_FirstAudioFormat(this->spec.format); test_format; test_format = SDL_NextAudioFormat()) {
switch (test_format) { switch (test_format) {
case AUDIO_U8: case AUDIO_U8:
case AUDIO_S16: case AUDIO_S16:
@ -321,20 +321,17 @@ WINMM_OpenDevice(_THIS, void *handle, const char *devname)
case AUDIO_F32: case AUDIO_F32:
this->spec.format = test_format; this->spec.format = test_format;
if (PrepWaveFormat(this, devId, &waveformat, iscapture)) { if (PrepWaveFormat(this, devId, &waveformat, iscapture)) {
valid_datatype = SDL_TRUE; break;
} else {
test_format = SDL_NextAudioFormat();
} }
break; continue;
default: default:
test_format = SDL_NextAudioFormat(); continue;
break;
} }
break;
} }
if (!valid_datatype) { if (!test_format) {
return SDL_SetError("Unsupported audio format"); return SDL_SetError("%s: Unsupported audio format", "winmm");
} }
/* Update the fragment size as size in bytes */ /* Update the fragment size as size in bytes */