src/audio/SDL_audio.c
author Ryan C. Gordon
Tue, 28 Feb 2017 19:48:52 -0500
changeset 10922 5f4b80b748dd
parent 10917 ef690a414f18
child 10935 9a4c02660fcf
permissions -rw-r--r--
raspberrypi: RPI_Destroy() should free the SDL_VideoDevice and its driverdata.
     1 /*
     2   Simple DirectMedia Layer
     3   Copyright (C) 1997-2017 Sam Lantinga <slouken@libsdl.org>
     4 
     5   This software is provided 'as-is', without any express or implied
     6   warranty.  In no event will the authors be held liable for any damages
     7   arising from the use of this software.
     8 
     9   Permission is granted to anyone to use this software for any purpose,
    10   including commercial applications, and to alter it and redistribute it
    11   freely, subject to the following restrictions:
    12 
    13   1. The origin of this software must not be misrepresented; you must not
    14      claim that you wrote the original software. If you use this software
    15      in a product, an acknowledgment in the product documentation would be
    16      appreciated but is not required.
    17   2. Altered source versions must be plainly marked as such, and must not be
    18      misrepresented as being the original software.
    19   3. This notice may not be removed or altered from any source distribution.
    20 */
    21 #include "../SDL_internal.h"
    22 
    23 /* Allow access to a raw mixing buffer */
    24 
    25 #include "SDL.h"
    26 #include "SDL_audio.h"
    27 #include "SDL_audio_c.h"
    28 #include "SDL_sysaudio.h"
    29 #include "../thread/SDL_systhread.h"
    30 
    31 #define _THIS SDL_AudioDevice *_this
    32 
    33 static SDL_AudioDriver current_audio;
    34 static SDL_AudioDevice *open_devices[16];
    35 
    36 /* Available audio drivers */
    37 static const AudioBootStrap *const bootstrap[] = {
    38 #if SDL_AUDIO_DRIVER_PULSEAUDIO
    39     &PULSEAUDIO_bootstrap,
    40 #endif
    41 #if SDL_AUDIO_DRIVER_ALSA
    42     &ALSA_bootstrap,
    43 #endif
    44 #if SDL_AUDIO_DRIVER_SNDIO
    45     &SNDIO_bootstrap,
    46 #endif
    47 #if SDL_AUDIO_DRIVER_BSD
    48     &BSD_AUDIO_bootstrap,
    49 #endif
    50 #if SDL_AUDIO_DRIVER_OSS
    51     &DSP_bootstrap,
    52 #endif
    53 #if SDL_AUDIO_DRIVER_QSA
    54     &QSAAUDIO_bootstrap,
    55 #endif
    56 #if SDL_AUDIO_DRIVER_SUNAUDIO
    57     &SUNAUDIO_bootstrap,
    58 #endif
    59 #if SDL_AUDIO_DRIVER_ARTS
    60     &ARTS_bootstrap,
    61 #endif
    62 #if SDL_AUDIO_DRIVER_ESD
    63     &ESD_bootstrap,
    64 #endif
    65 #if SDL_AUDIO_DRIVER_NACL
    66     &NACLAUDIO_bootstrap,
    67 #endif
    68 #if SDL_AUDIO_DRIVER_NAS
    69     &NAS_bootstrap,
    70 #endif
    71 #if SDL_AUDIO_DRIVER_WASAPI
    72     &WASAPI_bootstrap,
    73 #endif
    74 #if SDL_AUDIO_DRIVER_XAUDIO2
    75     &XAUDIO2_bootstrap,
    76 #endif
    77 #if SDL_AUDIO_DRIVER_DSOUND
    78     &DSOUND_bootstrap,
    79 #endif
    80 #if SDL_AUDIO_DRIVER_WINMM
    81     &WINMM_bootstrap,
    82 #endif
    83 #if SDL_AUDIO_DRIVER_PAUDIO
    84     &PAUDIO_bootstrap,
    85 #endif
    86 #if SDL_AUDIO_DRIVER_HAIKU
    87     &HAIKUAUDIO_bootstrap,
    88 #endif
    89 #if SDL_AUDIO_DRIVER_COREAUDIO
    90     &COREAUDIO_bootstrap,
    91 #endif
    92 #if SDL_AUDIO_DRIVER_FUSIONSOUND
    93     &FUSIONSOUND_bootstrap,
    94 #endif
    95 #if SDL_AUDIO_DRIVER_ANDROID
    96     &ANDROIDAUDIO_bootstrap,
    97 #endif
    98 #if SDL_AUDIO_DRIVER_PSP
    99     &PSPAUDIO_bootstrap,
   100 #endif
   101 #if SDL_AUDIO_DRIVER_EMSCRIPTEN
   102     &EMSCRIPTENAUDIO_bootstrap,
   103 #endif
   104 #if SDL_AUDIO_DRIVER_DISK
   105     &DISKAUDIO_bootstrap,
   106 #endif
   107 #if SDL_AUDIO_DRIVER_DUMMY
   108     &DUMMYAUDIO_bootstrap,
   109 #endif
   110     NULL
   111 };
   112 
   113 
   114 #ifdef HAVE_LIBSAMPLERATE_H
   115 #ifdef SDL_LIBSAMPLERATE_DYNAMIC
   116 static void *SRC_lib = NULL;
   117 #endif
   118 SDL_bool SRC_available = SDL_FALSE;
   119 int SRC_converter = 0;
   120 SRC_STATE* (*SRC_src_new)(int converter_type, int channels, int *error) = NULL;
   121 int (*SRC_src_process)(SRC_STATE *state, SRC_DATA *data) = NULL;
   122 int (*SRC_src_reset)(SRC_STATE *state) = NULL;
   123 SRC_STATE* (*SRC_src_delete)(SRC_STATE *state) = NULL;
   124 const char* (*SRC_src_strerror)(int error) = NULL;
   125 
   126 static SDL_bool
   127 LoadLibSampleRate(void)
   128 {
   129     const char *hint = SDL_GetHint(SDL_HINT_AUDIO_RESAMPLING_MODE);
   130 
   131     SRC_available = SDL_FALSE;
   132     SRC_converter = 0;
   133 
   134     if (!hint || *hint == '0' || SDL_strcasecmp(hint, "default") == 0) {
   135         return SDL_FALSE;  /* don't load anything. */
   136     } else if (*hint == '1' || SDL_strcasecmp(hint, "fast") == 0) {
   137         SRC_converter = SRC_SINC_FASTEST;
   138     } else if (*hint == '2' || SDL_strcasecmp(hint, "medium") == 0) {
   139         SRC_converter = SRC_SINC_MEDIUM_QUALITY;
   140     } else if (*hint == '3' || SDL_strcasecmp(hint, "best") == 0) {
   141         SRC_converter = SRC_SINC_BEST_QUALITY;
   142     } else {
   143         return SDL_FALSE;  /* treat it like "default", don't load anything. */
   144     }
   145 
   146 #ifdef SDL_LIBSAMPLERATE_DYNAMIC
   147     SDL_assert(SRC_lib == NULL);
   148     SRC_lib = SDL_LoadObject(SDL_LIBSAMPLERATE_DYNAMIC);
   149     if (!SRC_lib) {
   150         return SDL_FALSE;
   151     }
   152 
   153     SRC_src_new = (SRC_STATE* (*)(int converter_type, int channels, int *error))SDL_LoadFunction(SRC_lib, "src_new");
   154     SRC_src_process = (int (*)(SRC_STATE *state, SRC_DATA *data))SDL_LoadFunction(SRC_lib, "src_process");
   155     SRC_src_reset = (int(*)(SRC_STATE *state))SDL_LoadFunction(SRC_lib, "src_reset");
   156     SRC_src_delete = (SRC_STATE* (*)(SRC_STATE *state))SDL_LoadFunction(SRC_lib, "src_delete");
   157     SRC_src_strerror = (const char* (*)(int error))SDL_LoadFunction(SRC_lib, "src_strerror");
   158 
   159     if (!SRC_src_new || !SRC_src_process || !SRC_src_reset || !SRC_src_delete || !SRC_src_strerror) {
   160         SDL_UnloadObject(SRC_lib);
   161         SRC_lib = NULL;
   162         return SDL_FALSE;
   163     }
   164 #else
   165     SRC_src_new = src_new;
   166     SRC_src_process = src_process;
   167     SRC_src_reset = src_reset;
   168     SRC_src_delete = src_delete;
   169     SRC_src_strerror = src_strerror;
   170 #endif
   171 
   172     SRC_available = SDL_TRUE;
   173     return SDL_TRUE;
   174 }
   175 
   176 static void
   177 UnloadLibSampleRate(void)
   178 {
   179 #ifdef SDL_LIBSAMPLERATE_DYNAMIC
   180     if (SRC_lib != NULL) {
   181         SDL_UnloadObject(SRC_lib);
   182     }
   183     SRC_lib = NULL;
   184 #endif
   185 
   186     SRC_available = SDL_FALSE;
   187     SRC_src_new = NULL;
   188     SRC_src_process = NULL;
   189     SRC_src_reset = NULL;
   190     SRC_src_delete = NULL;
   191     SRC_src_strerror = NULL;
   192 }
   193 #endif
   194 
   195 static SDL_AudioDevice *
   196 get_audio_device(SDL_AudioDeviceID id)
   197 {
   198     id--;
   199     if ((id >= SDL_arraysize(open_devices)) || (open_devices[id] == NULL)) {
   200         SDL_SetError("Invalid audio device ID");
   201         return NULL;
   202     }
   203 
   204     return open_devices[id];
   205 }
   206 
   207 
   208 /* stubs for audio drivers that don't need a specific entry point... */
   209 static void
   210 SDL_AudioDetectDevices_Default(void)
   211 {
   212     /* you have to write your own implementation if these assertions fail. */
   213     SDL_assert(current_audio.impl.OnlyHasDefaultOutputDevice);
   214     SDL_assert(current_audio.impl.OnlyHasDefaultCaptureDevice || !current_audio.impl.HasCaptureSupport);
   215 
   216     SDL_AddAudioDevice(SDL_FALSE, DEFAULT_OUTPUT_DEVNAME, (void *) ((size_t) 0x1));
   217     if (current_audio.impl.HasCaptureSupport) {
   218         SDL_AddAudioDevice(SDL_TRUE, DEFAULT_INPUT_DEVNAME, (void *) ((size_t) 0x2));
   219     }
   220 }
   221 
   222 static void
   223 SDL_AudioThreadInit_Default(_THIS)
   224 {                               /* no-op. */
   225 }
   226 
   227 static void
   228 SDL_AudioThreadDeinit_Default(_THIS)
   229 {                               /* no-op. */
   230 }
   231 
   232 static void
   233 SDL_AudioWaitDevice_Default(_THIS)
   234 {                               /* no-op. */
   235 }
   236 
   237 static void
   238 SDL_AudioPlayDevice_Default(_THIS)
   239 {                               /* no-op. */
   240 }
   241 
   242 static int
   243 SDL_AudioGetPendingBytes_Default(_THIS)
   244 {
   245     return 0;
   246 }
   247 
   248 static Uint8 *
   249 SDL_AudioGetDeviceBuf_Default(_THIS)
   250 {
   251     return NULL;
   252 }
   253 
   254 static int
   255 SDL_AudioCaptureFromDevice_Default(_THIS, void *buffer, int buflen)
   256 {
   257     return -1;  /* just fail immediately. */
   258 }
   259 
   260 static void
   261 SDL_AudioFlushCapture_Default(_THIS)
   262 {                               /* no-op. */
   263 }
   264 
   265 static void
   266 SDL_AudioPrepareToClose_Default(_THIS)
   267 {                               /* no-op. */
   268 }
   269 
   270 static void
   271 SDL_AudioCloseDevice_Default(_THIS)
   272 {                               /* no-op. */
   273 }
   274 
   275 static void
   276 SDL_AudioDeinitialize_Default(void)
   277 {                               /* no-op. */
   278 }
   279 
   280 static void
   281 SDL_AudioFreeDeviceHandle_Default(void *handle)
   282 {                               /* no-op. */
   283 }
   284 
   285 
   286 static int
   287 SDL_AudioOpenDevice_Default(_THIS, void *handle, const char *devname, int iscapture)
   288 {
   289     return SDL_Unsupported();
   290 }
   291 
   292 static SDL_INLINE SDL_bool
   293 is_in_audio_device_thread(SDL_AudioDevice * device)
   294 {
   295     /* The device thread locks the same mutex, but not through the public API.
   296        This check is in case the application, in the audio callback,
   297        tries to lock the thread that we've already locked from the
   298        device thread...just in case we only have non-recursive mutexes. */
   299     if (device->thread && (SDL_ThreadID() == device->threadid)) {
   300         return SDL_TRUE;
   301     }
   302 
   303     return SDL_FALSE;
   304 }
   305 
   306 static void
   307 SDL_AudioLockDevice_Default(SDL_AudioDevice * device)
   308 {
   309     if (!is_in_audio_device_thread(device)) {
   310         SDL_LockMutex(device->mixer_lock);
   311     }
   312 }
   313 
   314 static void
   315 SDL_AudioUnlockDevice_Default(SDL_AudioDevice * device)
   316 {
   317     if (!is_in_audio_device_thread(device)) {
   318         SDL_UnlockMutex(device->mixer_lock);
   319     }
   320 }
   321 
   322 static void
   323 SDL_AudioLockOrUnlockDeviceWithNoMixerLock(SDL_AudioDevice * device)
   324 {
   325 }
   326 
   327 static void
   328 finish_audio_entry_points_init(void)
   329 {
   330     /*
   331      * Fill in stub functions for unused driver entry points. This lets us
   332      *  blindly call them without having to check for validity first.
   333      */
   334 
   335     if (current_audio.impl.SkipMixerLock) {
   336         if (current_audio.impl.LockDevice == NULL) {
   337             current_audio.impl.LockDevice = SDL_AudioLockOrUnlockDeviceWithNoMixerLock;
   338         }
   339         if (current_audio.impl.UnlockDevice == NULL) {
   340             current_audio.impl.UnlockDevice = SDL_AudioLockOrUnlockDeviceWithNoMixerLock;
   341         }
   342     }
   343 
   344 #define FILL_STUB(x) \
   345         if (current_audio.impl.x == NULL) { \
   346             current_audio.impl.x = SDL_Audio##x##_Default; \
   347         }
   348     FILL_STUB(DetectDevices);
   349     FILL_STUB(OpenDevice);
   350     FILL_STUB(ThreadInit);
   351     FILL_STUB(ThreadDeinit);
   352     FILL_STUB(WaitDevice);
   353     FILL_STUB(PlayDevice);
   354     FILL_STUB(GetPendingBytes);
   355     FILL_STUB(GetDeviceBuf);
   356     FILL_STUB(CaptureFromDevice);
   357     FILL_STUB(FlushCapture);
   358     FILL_STUB(PrepareToClose);
   359     FILL_STUB(CloseDevice);
   360     FILL_STUB(LockDevice);
   361     FILL_STUB(UnlockDevice);
   362     FILL_STUB(FreeDeviceHandle);
   363     FILL_STUB(Deinitialize);
   364 #undef FILL_STUB
   365 }
   366 
   367 
   368 /* device hotplug support... */
   369 
   370 static int
   371 add_audio_device(const char *name, void *handle, SDL_AudioDeviceItem **devices, int *devCount)
   372 {
   373     int retval = -1;
   374     const size_t size = sizeof (SDL_AudioDeviceItem) + SDL_strlen(name) + 1;
   375     SDL_AudioDeviceItem *item = (SDL_AudioDeviceItem *) SDL_malloc(size);
   376     if (item == NULL) {
   377         return -1;
   378     }
   379 
   380     SDL_assert(handle != NULL);  /* we reserve NULL, audio backends can't use it. */
   381 
   382     item->handle = handle;
   383     SDL_strlcpy(item->name, name, size - sizeof (SDL_AudioDeviceItem));
   384 
   385     SDL_LockMutex(current_audio.detectionLock);
   386     item->next = *devices;
   387     *devices = item;
   388     retval = (*devCount)++;
   389     SDL_UnlockMutex(current_audio.detectionLock);
   390 
   391     return retval;
   392 }
   393 
   394 static SDL_INLINE int
   395 add_capture_device(const char *name, void *handle)
   396 {
   397     SDL_assert(current_audio.impl.HasCaptureSupport);
   398     return add_audio_device(name, handle, &current_audio.inputDevices, &current_audio.inputDeviceCount);
   399 }
   400 
   401 static SDL_INLINE int
   402 add_output_device(const char *name, void *handle)
   403 {
   404     return add_audio_device(name, handle, &current_audio.outputDevices, &current_audio.outputDeviceCount);
   405 }
   406 
   407 static void
   408 free_device_list(SDL_AudioDeviceItem **devices, int *devCount)
   409 {
   410     SDL_AudioDeviceItem *item, *next;
   411     for (item = *devices; item != NULL; item = next) {
   412         next = item->next;
   413         if (item->handle != NULL) {
   414             current_audio.impl.FreeDeviceHandle(item->handle);
   415         }
   416         SDL_free(item);
   417     }
   418     *devices = NULL;
   419     *devCount = 0;
   420 }
   421 
   422 
   423 /* The audio backends call this when a new device is plugged in. */
   424 void
   425 SDL_AddAudioDevice(const int iscapture, const char *name, void *handle)
   426 {
   427     const int device_index = iscapture ? add_capture_device(name, handle) : add_output_device(name, handle);
   428     if (device_index != -1) {
   429         /* Post the event, if desired */
   430         if (SDL_GetEventState(SDL_AUDIODEVICEADDED) == SDL_ENABLE) {
   431             SDL_Event event;
   432             SDL_zero(event);
   433             event.adevice.type = SDL_AUDIODEVICEADDED;
   434             event.adevice.which = device_index;
   435             event.adevice.iscapture = iscapture;
   436             SDL_PushEvent(&event);
   437         }
   438     }
   439 }
   440 
   441 /* The audio backends call this when a currently-opened device is lost. */
   442 void SDL_OpenedAudioDeviceDisconnected(SDL_AudioDevice *device)
   443 {
   444     SDL_assert(get_audio_device(device->id) == device);
   445 
   446     if (!SDL_AtomicGet(&device->enabled)) {
   447         return;
   448     }
   449 
   450     /* Ends the audio callback and mark the device as STOPPED, but the
   451        app still needs to close the device to free resources. */
   452     current_audio.impl.LockDevice(device);
   453     SDL_AtomicSet(&device->enabled, 0);
   454     current_audio.impl.UnlockDevice(device);
   455 
   456     /* Post the event, if desired */
   457     if (SDL_GetEventState(SDL_AUDIODEVICEREMOVED) == SDL_ENABLE) {
   458         SDL_Event event;
   459         SDL_zero(event);
   460         event.adevice.type = SDL_AUDIODEVICEREMOVED;
   461         event.adevice.which = device->id;
   462         event.adevice.iscapture = device->iscapture ? 1 : 0;
   463         SDL_PushEvent(&event);
   464     }
   465 }
   466 
   467 static void
   468 mark_device_removed(void *handle, SDL_AudioDeviceItem *devices, SDL_bool *removedFlag)
   469 {
   470     SDL_AudioDeviceItem *item;
   471     SDL_assert(handle != NULL);
   472     for (item = devices; item != NULL; item = item->next) {
   473         if (item->handle == handle) {
   474             item->handle = NULL;
   475             *removedFlag = SDL_TRUE;
   476             return;
   477         }
   478     }
   479 }
   480 
   481 /* The audio backends call this when a device is removed from the system. */
   482 void
   483 SDL_RemoveAudioDevice(const int iscapture, void *handle)
   484 {
   485     int device_index;
   486     SDL_AudioDevice *device = NULL;
   487 
   488     SDL_LockMutex(current_audio.detectionLock);
   489     if (iscapture) {
   490         mark_device_removed(handle, current_audio.inputDevices, &current_audio.captureDevicesRemoved);
   491     } else {
   492         mark_device_removed(handle, current_audio.outputDevices, &current_audio.outputDevicesRemoved);
   493     }
   494     for (device_index = 0; device_index < SDL_arraysize(open_devices); device_index++)
   495     {
   496         device = open_devices[device_index];
   497         if (device != NULL && device->handle == handle)
   498         {
   499             SDL_OpenedAudioDeviceDisconnected(device);
   500             break;
   501         }
   502     }
   503     SDL_UnlockMutex(current_audio.detectionLock);
   504 
   505     current_audio.impl.FreeDeviceHandle(handle);
   506 }
   507 
   508 
   509 
   510 /* buffer queueing support... */
   511 
   512 static void SDLCALL
   513 SDL_BufferQueueDrainCallback(void *userdata, Uint8 *stream, int len)
   514 {
   515     /* this function always holds the mixer lock before being called. */
   516     SDL_AudioDevice *device = (SDL_AudioDevice *) userdata;
   517     size_t dequeued;
   518 
   519     SDL_assert(device != NULL);  /* this shouldn't ever happen, right?! */
   520     SDL_assert(!device->iscapture);  /* this shouldn't ever happen, right?! */
   521     SDL_assert(len >= 0);  /* this shouldn't ever happen, right?! */
   522 
   523     dequeued = SDL_ReadFromDataQueue(device->buffer_queue, stream, len);
   524     stream += dequeued;
   525     len -= (int) dequeued;
   526 
   527     if (len > 0) {  /* fill any remaining space in the stream with silence. */
   528         SDL_assert(SDL_CountDataQueue(device->buffer_queue) == 0);
   529         SDL_memset(stream, device->spec.silence, len);
   530     }
   531 }
   532 
   533 static void SDLCALL
   534 SDL_BufferQueueFillCallback(void *userdata, Uint8 *stream, int len)
   535 {
   536     /* this function always holds the mixer lock before being called. */
   537     SDL_AudioDevice *device = (SDL_AudioDevice *) userdata;
   538 
   539     SDL_assert(device != NULL);  /* this shouldn't ever happen, right?! */
   540     SDL_assert(device->iscapture);  /* this shouldn't ever happen, right?! */
   541     SDL_assert(len >= 0);  /* this shouldn't ever happen, right?! */
   542 
   543     /* note that if this needs to allocate more space and run out of memory,
   544        we have no choice but to quietly drop the data and hope it works out
   545        later, but you probably have bigger problems in this case anyhow. */
   546     SDL_WriteToDataQueue(device->buffer_queue, stream, len);
   547 }
   548 
   549 int
   550 SDL_QueueAudio(SDL_AudioDeviceID devid, const void *data, Uint32 len)
   551 {
   552     SDL_AudioDevice *device = get_audio_device(devid);
   553     int rc = 0;
   554 
   555     if (!device) {
   556         return -1;  /* get_audio_device() will have set the error state */
   557     } else if (device->iscapture) {
   558         return SDL_SetError("This is a capture device, queueing not allowed");
   559     } else if (device->spec.callback != SDL_BufferQueueDrainCallback) {
   560         return SDL_SetError("Audio device has a callback, queueing not allowed");
   561     }
   562 
   563     if (len > 0) {
   564         current_audio.impl.LockDevice(device);
   565         rc = SDL_WriteToDataQueue(device->buffer_queue, data, len);
   566         current_audio.impl.UnlockDevice(device);
   567     }
   568 
   569     return rc;
   570 }
   571 
   572 Uint32
   573 SDL_DequeueAudio(SDL_AudioDeviceID devid, void *data, Uint32 len)
   574 {
   575     SDL_AudioDevice *device = get_audio_device(devid);
   576     Uint32 rc;
   577 
   578     if ( (len == 0) ||  /* nothing to do? */
   579          (!device) ||  /* called with bogus device id */
   580          (!device->iscapture) ||  /* playback devices can't dequeue */
   581          (device->spec.callback != SDL_BufferQueueFillCallback) ) { /* not set for queueing */
   582         return 0;  /* just report zero bytes dequeued. */
   583     }
   584 
   585     current_audio.impl.LockDevice(device);
   586     rc = (Uint32) SDL_ReadFromDataQueue(device->buffer_queue, data, len);
   587     current_audio.impl.UnlockDevice(device);
   588     return rc;
   589 }
   590 
   591 Uint32
   592 SDL_GetQueuedAudioSize(SDL_AudioDeviceID devid)
   593 {
   594     Uint32 retval = 0;
   595     SDL_AudioDevice *device = get_audio_device(devid);
   596 
   597     if (!device) {
   598         return 0;
   599     }
   600 
   601     /* Nothing to do unless we're set up for queueing. */
   602     if (device->spec.callback == SDL_BufferQueueDrainCallback) {
   603         current_audio.impl.LockDevice(device);
   604         retval = ((Uint32) SDL_CountDataQueue(device->buffer_queue)) + current_audio.impl.GetPendingBytes(device);
   605         current_audio.impl.UnlockDevice(device);
   606     } else if (device->spec.callback == SDL_BufferQueueFillCallback) {
   607         current_audio.impl.LockDevice(device);
   608         retval = (Uint32) SDL_CountDataQueue(device->buffer_queue);
   609         current_audio.impl.UnlockDevice(device);
   610     }
   611 
   612     return retval;
   613 }
   614 
   615 void
   616 SDL_ClearQueuedAudio(SDL_AudioDeviceID devid)
   617 {
   618     SDL_AudioDevice *device = get_audio_device(devid);
   619 
   620     if (!device) {
   621         return;  /* nothing to do. */
   622     }
   623 
   624     /* Blank out the device and release the mutex. Free it afterwards. */
   625     current_audio.impl.LockDevice(device);
   626 
   627     /* Keep up to two packets in the pool to reduce future malloc pressure. */
   628     SDL_ClearDataQueue(device->buffer_queue, SDL_AUDIOBUFFERQUEUE_PACKETLEN * 2);
   629 
   630     current_audio.impl.UnlockDevice(device);
   631 }
   632 
   633 
   634 /* The general mixing thread function */
   635 static int SDLCALL
   636 SDL_RunAudio(void *devicep)
   637 {
   638     SDL_AudioDevice *device = (SDL_AudioDevice *) devicep;
   639     const int silence = (int) device->spec.silence;
   640     const Uint32 delay = ((device->spec.samples * 1000) / device->spec.freq);
   641     const int data_len = device->callbackspec.size;
   642     Uint8 *data;
   643     void *udata = device->spec.userdata;
   644     SDL_AudioCallback callback = device->spec.callback;
   645 
   646     SDL_assert(!device->iscapture);
   647 
   648     /* The audio mixing is always a high priority thread */
   649     SDL_SetThreadPriority(SDL_THREAD_PRIORITY_HIGH);
   650 
   651     /* Perform any thread setup */
   652     device->threadid = SDL_ThreadID();
   653     current_audio.impl.ThreadInit(device);
   654 
   655     /* Loop, filling the audio buffers */
   656     while (!SDL_AtomicGet(&device->shutdown)) {
   657         /* Fill the current buffer with sound */
   658         if (!device->stream && SDL_AtomicGet(&device->enabled)) {
   659             SDL_assert(data_len == device->spec.size);
   660             data = current_audio.impl.GetDeviceBuf(device);
   661         } else {
   662             /* if the device isn't enabled, we still write to the
   663                work_buffer, so the app's callback will fire with
   664                a regular frequency, in case they depend on that
   665                for timing or progress. They can use hotplug
   666                now to know if the device failed.
   667                Streaming playback uses work_buffer, too. */
   668             data = NULL;
   669         }
   670 
   671         if (data == NULL) {
   672             data = device->work_buffer;
   673         }
   674 
   675         /* !!! FIXME: this should be LockDevice. */
   676         SDL_LockMutex(device->mixer_lock);
   677         if (SDL_AtomicGet(&device->paused)) {
   678             SDL_memset(data, silence, data_len);
   679         } else {
   680             callback(udata, data, data_len);
   681         }
   682         SDL_UnlockMutex(device->mixer_lock);
   683 
   684         if (device->stream) {
   685             /* Stream available audio to device, converting/resampling. */
   686             /* if this fails...oh well. We'll play silence here. */
   687             SDL_AudioStreamPut(device->stream, data, data_len);
   688 
   689             while (SDL_AudioStreamAvailable(device->stream) >= ((int) device->spec.size)) {
   690                 int got;
   691                 data = SDL_AtomicGet(&device->enabled) ? current_audio.impl.GetDeviceBuf(device) : NULL;
   692                 got = SDL_AudioStreamGet(device->stream, data ? data : device->work_buffer, device->spec.size);
   693                 SDL_assert((got < 0) || (got == device->spec.size));
   694 
   695                 if (data == NULL) {  /* device is having issues... */
   696                     SDL_Delay(delay);  /* wait for as long as this buffer would have played. Maybe device recovers later? */
   697                 } else {
   698                     if (got != device->spec.size) {
   699                         SDL_memset(data, device->spec.silence, device->spec.size);
   700                     }
   701                     current_audio.impl.PlayDevice(device);
   702                     current_audio.impl.WaitDevice(device);
   703                 }
   704             }
   705         } else if (data == device->work_buffer) {
   706             /* nothing to do; pause like we queued a buffer to play. */
   707             SDL_Delay(delay);
   708         } else {  /* writing directly to the device. */
   709             /* queue this buffer and wait for it to finish playing. */
   710             current_audio.impl.PlayDevice(device);
   711             current_audio.impl.WaitDevice(device);
   712         }
   713     }
   714 
   715     current_audio.impl.PrepareToClose(device);
   716 
   717     /* Wait for the audio to drain. */
   718     SDL_Delay(((device->spec.samples * 1000) / device->spec.freq) * 2);
   719 
   720     current_audio.impl.ThreadDeinit(device);
   721 
   722     return 0;
   723 }
   724 
   725 /* The general capture thread function */
   726 static int SDLCALL
   727 SDL_CaptureAudio(void *devicep)
   728 {
   729     SDL_AudioDevice *device = (SDL_AudioDevice *) devicep;
   730     const int silence = (int) device->spec.silence;
   731     const Uint32 delay = ((device->spec.samples * 1000) / device->spec.freq);
   732     const int data_len = device->spec.size;
   733     Uint8 *data;
   734     void *udata = device->spec.userdata;
   735     SDL_AudioCallback callback = device->spec.callback;
   736 
   737     SDL_assert(device->iscapture);
   738 
   739     /* The audio mixing is always a high priority thread */
   740     SDL_SetThreadPriority(SDL_THREAD_PRIORITY_HIGH);
   741 
   742     /* Perform any thread setup */
   743     device->threadid = SDL_ThreadID();
   744     current_audio.impl.ThreadInit(device);
   745 
   746     /* Loop, filling the audio buffers */
   747     while (!SDL_AtomicGet(&device->shutdown)) {
   748         int still_need;
   749         Uint8 *ptr;
   750 
   751         if (SDL_AtomicGet(&device->paused)) {
   752             SDL_Delay(delay);  /* just so we don't cook the CPU. */
   753             if (device->stream) {
   754                 SDL_AudioStreamClear(device->stream);
   755             }
   756             current_audio.impl.FlushCapture(device);  /* dump anything pending. */
   757             continue;
   758         }
   759 
   760         /* Fill the current buffer with sound */
   761         still_need = data_len;
   762 
   763         /* Use the work_buffer to hold data read from the device. */
   764         data = device->work_buffer;
   765         SDL_assert(data != NULL);
   766 
   767         ptr = data;
   768 
   769         /* We still read from the device when "paused" to keep the state sane,
   770            and block when there isn't data so this thread isn't eating CPU.
   771            But we don't process it further or call the app's callback. */
   772 
   773         if (!SDL_AtomicGet(&device->enabled)) {
   774             SDL_Delay(delay);  /* try to keep callback firing at normal pace. */
   775         } else {
   776             while (still_need > 0) {
   777                 const int rc = current_audio.impl.CaptureFromDevice(device, ptr, still_need);
   778                 SDL_assert(rc <= still_need);  /* device should not overflow buffer. :) */
   779                 if (rc > 0) {
   780                     still_need -= rc;
   781                     ptr += rc;
   782                 } else {  /* uhoh, device failed for some reason! */
   783                     SDL_OpenedAudioDeviceDisconnected(device);
   784                     break;
   785                 }
   786             }
   787         }
   788 
   789         if (still_need > 0) {
   790             /* Keep any data we already read, silence the rest. */
   791             SDL_memset(ptr, silence, still_need);
   792         }
   793 
   794         if (device->stream) {
   795             /* if this fails...oh well. */
   796             SDL_AudioStreamPut(device->stream, data, data_len);
   797 
   798             while (SDL_AudioStreamAvailable(device->stream) >= ((int) device->callbackspec.size)) {
   799                 const int got = SDL_AudioStreamGet(device->stream, device->work_buffer, device->callbackspec.size);
   800                 SDL_assert((got < 0) || (got == device->callbackspec.size));
   801                 if (got != device->callbackspec.size) {
   802                     SDL_memset(device->work_buffer, device->spec.silence, device->callbackspec.size);
   803                 }
   804 
   805                 /* !!! FIXME: this should be LockDevice. */
   806                 SDL_LockMutex(device->mixer_lock);
   807                 if (!SDL_AtomicGet(&device->paused)) {
   808                     callback(udata, device->work_buffer, device->callbackspec.size);
   809                 }
   810                 SDL_UnlockMutex(device->mixer_lock);
   811             }
   812         } else {  /* feeding user callback directly without streaming. */
   813             /* !!! FIXME: this should be LockDevice. */
   814             SDL_LockMutex(device->mixer_lock);
   815             if (!SDL_AtomicGet(&device->paused)) {
   816                 callback(udata, data, device->callbackspec.size);
   817             }
   818             SDL_UnlockMutex(device->mixer_lock);
   819         }
   820     }
   821 
   822     current_audio.impl.FlushCapture(device);
   823 
   824     current_audio.impl.ThreadDeinit(device);
   825 
   826     return 0;
   827 }
   828 
   829 
   830 static SDL_AudioFormat
   831 SDL_ParseAudioFormat(const char *string)
   832 {
   833 #define CHECK_FMT_STRING(x) if (SDL_strcmp(string, #x) == 0) return AUDIO_##x
   834     CHECK_FMT_STRING(U8);
   835     CHECK_FMT_STRING(S8);
   836     CHECK_FMT_STRING(U16LSB);
   837     CHECK_FMT_STRING(S16LSB);
   838     CHECK_FMT_STRING(U16MSB);
   839     CHECK_FMT_STRING(S16MSB);
   840     CHECK_FMT_STRING(U16SYS);
   841     CHECK_FMT_STRING(S16SYS);
   842     CHECK_FMT_STRING(U16);
   843     CHECK_FMT_STRING(S16);
   844     CHECK_FMT_STRING(S32LSB);
   845     CHECK_FMT_STRING(S32MSB);
   846     CHECK_FMT_STRING(S32SYS);
   847     CHECK_FMT_STRING(S32);
   848     CHECK_FMT_STRING(F32LSB);
   849     CHECK_FMT_STRING(F32MSB);
   850     CHECK_FMT_STRING(F32SYS);
   851     CHECK_FMT_STRING(F32);
   852 #undef CHECK_FMT_STRING
   853     return 0;
   854 }
   855 
   856 int
   857 SDL_GetNumAudioDrivers(void)
   858 {
   859     return SDL_arraysize(bootstrap) - 1;
   860 }
   861 
   862 const char *
   863 SDL_GetAudioDriver(int index)
   864 {
   865     if (index >= 0 && index < SDL_GetNumAudioDrivers()) {
   866         return bootstrap[index]->name;
   867     }
   868     return NULL;
   869 }
   870 
   871 extern void SDL_ChooseAudioConverters(void);
   872 
   873 int
   874 SDL_AudioInit(const char *driver_name)
   875 {
   876     int i = 0;
   877     int initialized = 0;
   878     int tried_to_init = 0;
   879 
   880     if (SDL_WasInit(SDL_INIT_AUDIO)) {
   881         SDL_AudioQuit();        /* shutdown driver if already running. */
   882     }
   883 
   884     SDL_zero(current_audio);
   885     SDL_zero(open_devices);
   886 
   887     SDL_ChooseAudioConverters();
   888 
   889     /* Select the proper audio driver */
   890     if (driver_name == NULL) {
   891         driver_name = SDL_getenv("SDL_AUDIODRIVER");
   892     }
   893 
   894     for (i = 0; (!initialized) && (bootstrap[i]); ++i) {
   895         /* make sure we should even try this driver before doing so... */
   896         const AudioBootStrap *backend = bootstrap[i];
   897         if ((driver_name && (SDL_strncasecmp(backend->name, driver_name, SDL_strlen(driver_name)) != 0)) ||
   898             (!driver_name && backend->demand_only)) {
   899             continue;
   900         }
   901 
   902         tried_to_init = 1;
   903         SDL_zero(current_audio);
   904         current_audio.name = backend->name;
   905         current_audio.desc = backend->desc;
   906         initialized = backend->init(&current_audio.impl);
   907     }
   908 
   909     if (!initialized) {
   910         /* specific drivers will set the error message if they fail... */
   911         if (!tried_to_init) {
   912             if (driver_name) {
   913                 SDL_SetError("Audio target '%s' not available", driver_name);
   914             } else {
   915                 SDL_SetError("No available audio device");
   916             }
   917         }
   918 
   919         SDL_zero(current_audio);
   920         return -1;            /* No driver was available, so fail. */
   921     }
   922 
   923     current_audio.detectionLock = SDL_CreateMutex();
   924 
   925     finish_audio_entry_points_init();
   926 
   927     /* Make sure we have a list of devices available at startup. */
   928     current_audio.impl.DetectDevices();
   929 
   930 #ifdef HAVE_LIBSAMPLERATE_H
   931     LoadLibSampleRate();
   932 #endif
   933 
   934     return 0;
   935 }
   936 
   937 /*
   938  * Get the current audio driver name
   939  */
   940 const char *
   941 SDL_GetCurrentAudioDriver()
   942 {
   943     return current_audio.name;
   944 }
   945 
   946 /* Clean out devices that we've removed but had to keep around for stability. */
   947 static void
   948 clean_out_device_list(SDL_AudioDeviceItem **devices, int *devCount, SDL_bool *removedFlag)
   949 {
   950     SDL_AudioDeviceItem *item = *devices;
   951     SDL_AudioDeviceItem *prev = NULL;
   952     int total = 0;
   953 
   954     while (item) {
   955         SDL_AudioDeviceItem *next = item->next;
   956         if (item->handle != NULL) {
   957             total++;
   958             prev = item;
   959         } else {
   960             if (prev) {
   961                 prev->next = next;
   962             } else {
   963                 *devices = next;
   964             }
   965             SDL_free(item);
   966         }
   967         item = next;
   968     }
   969 
   970     *devCount = total;
   971     *removedFlag = SDL_FALSE;
   972 }
   973 
   974 
   975 int
   976 SDL_GetNumAudioDevices(int iscapture)
   977 {
   978     int retval = 0;
   979 
   980     if (!SDL_WasInit(SDL_INIT_AUDIO)) {
   981         return -1;
   982     }
   983 
   984     SDL_LockMutex(current_audio.detectionLock);
   985     if (iscapture && current_audio.captureDevicesRemoved) {
   986         clean_out_device_list(&current_audio.inputDevices, &current_audio.inputDeviceCount, &current_audio.captureDevicesRemoved);
   987     }
   988 
   989     if (!iscapture && current_audio.outputDevicesRemoved) {
   990         clean_out_device_list(&current_audio.outputDevices, &current_audio.outputDeviceCount, &current_audio.outputDevicesRemoved);
   991         current_audio.outputDevicesRemoved = SDL_FALSE;
   992     }
   993 
   994     retval = iscapture ? current_audio.inputDeviceCount : current_audio.outputDeviceCount;
   995     SDL_UnlockMutex(current_audio.detectionLock);
   996 
   997     return retval;
   998 }
   999 
  1000 
  1001 const char *
  1002 SDL_GetAudioDeviceName(int index, int iscapture)
  1003 {
  1004     const char *retval = NULL;
  1005 
  1006     if (!SDL_WasInit(SDL_INIT_AUDIO)) {
  1007         SDL_SetError("Audio subsystem is not initialized");
  1008         return NULL;
  1009     }
  1010 
  1011     if ((iscapture) && (!current_audio.impl.HasCaptureSupport)) {
  1012         SDL_SetError("No capture support");
  1013         return NULL;
  1014     }
  1015 
  1016     if (index >= 0) {
  1017         SDL_AudioDeviceItem *item;
  1018         int i;
  1019 
  1020         SDL_LockMutex(current_audio.detectionLock);
  1021         item = iscapture ? current_audio.inputDevices : current_audio.outputDevices;
  1022         i = iscapture ? current_audio.inputDeviceCount : current_audio.outputDeviceCount;
  1023         if (index < i) {
  1024             for (i--; i > index; i--, item = item->next) {
  1025                 SDL_assert(item != NULL);
  1026             }
  1027             SDL_assert(item != NULL);
  1028             retval = item->name;
  1029         }
  1030         SDL_UnlockMutex(current_audio.detectionLock);
  1031     }
  1032 
  1033     if (retval == NULL) {
  1034         SDL_SetError("No such device");
  1035     }
  1036 
  1037     return retval;
  1038 }
  1039 
  1040 
  1041 static void
  1042 close_audio_device(SDL_AudioDevice * device)
  1043 {
  1044     if (!device) {
  1045         return;
  1046     }
  1047 
  1048     if (device->id > 0) {
  1049         SDL_AudioDevice *opendev = open_devices[device->id - 1];
  1050         SDL_assert((opendev == device) || (opendev == NULL));
  1051         if (opendev == device) {
  1052             open_devices[device->id - 1] = NULL;
  1053         }
  1054     }
  1055 
  1056     SDL_AtomicSet(&device->shutdown, 1);
  1057     SDL_AtomicSet(&device->enabled, 0);
  1058     if (device->thread != NULL) {
  1059         SDL_WaitThread(device->thread, NULL);
  1060     }
  1061     if (device->mixer_lock != NULL) {
  1062         SDL_DestroyMutex(device->mixer_lock);
  1063     }
  1064 
  1065     SDL_free(device->work_buffer);
  1066     SDL_FreeAudioStream(device->stream);
  1067 
  1068     if (device->hidden != NULL) {
  1069         current_audio.impl.CloseDevice(device);
  1070     }
  1071 
  1072     SDL_FreeDataQueue(device->buffer_queue);
  1073 
  1074     SDL_free(device);
  1075 }
  1076 
  1077 
  1078 /*
  1079  * Sanity check desired AudioSpec for SDL_OpenAudio() in (orig).
  1080  *  Fills in a sanitized copy in (prepared).
  1081  *  Returns non-zero if okay, zero on fatal parameters in (orig).
  1082  */
  1083 static int
  1084 prepare_audiospec(const SDL_AudioSpec * orig, SDL_AudioSpec * prepared)
  1085 {
  1086     SDL_memcpy(prepared, orig, sizeof(SDL_AudioSpec));
  1087 
  1088     if (orig->freq == 0) {
  1089         const char *env = SDL_getenv("SDL_AUDIO_FREQUENCY");
  1090         if ((!env) || ((prepared->freq = SDL_atoi(env)) == 0)) {
  1091             prepared->freq = 22050;     /* a reasonable default */
  1092         }
  1093     }
  1094 
  1095     if (orig->format == 0) {
  1096         const char *env = SDL_getenv("SDL_AUDIO_FORMAT");
  1097         if ((!env) || ((prepared->format = SDL_ParseAudioFormat(env)) == 0)) {
  1098             prepared->format = AUDIO_S16;       /* a reasonable default */
  1099         }
  1100     }
  1101 
  1102     switch (orig->channels) {
  1103     case 0:{
  1104             const char *env = SDL_getenv("SDL_AUDIO_CHANNELS");
  1105             if ((!env) || ((prepared->channels = (Uint8) SDL_atoi(env)) == 0)) {
  1106                 prepared->channels = 2; /* a reasonable default */
  1107             }
  1108             break;
  1109         }
  1110     case 1:                    /* Mono */
  1111     case 2:                    /* Stereo */
  1112     case 4:                    /* surround */
  1113     case 6:                    /* surround with center and lfe */
  1114         break;
  1115     default:
  1116         SDL_SetError("Unsupported number of audio channels.");
  1117         return 0;
  1118     }
  1119 
  1120     if (orig->samples == 0) {
  1121         const char *env = SDL_getenv("SDL_AUDIO_SAMPLES");
  1122         if ((!env) || ((prepared->samples = (Uint16) SDL_atoi(env)) == 0)) {
  1123             /* Pick a default of ~46 ms at desired frequency */
  1124             /* !!! FIXME: remove this when the non-Po2 resampling is in. */
  1125             const int samples = (prepared->freq / 1000) * 46;
  1126             int power2 = 1;
  1127             while (power2 < samples) {
  1128                 power2 *= 2;
  1129             }
  1130             prepared->samples = power2;
  1131         }
  1132     }
  1133 
  1134     /* Calculate the silence and size of the audio specification */
  1135     SDL_CalculateAudioSpec(prepared);
  1136 
  1137     return 1;
  1138 }
  1139 
  1140 static SDL_AudioDeviceID
  1141 open_audio_device(const char *devname, int iscapture,
  1142                   const SDL_AudioSpec * desired, SDL_AudioSpec * obtained,
  1143                   int allowed_changes, int min_id)
  1144 {
  1145     const SDL_bool is_internal_thread = (desired->callback == NULL);
  1146     SDL_AudioDeviceID id = 0;
  1147     SDL_AudioSpec _obtained;
  1148     SDL_AudioDevice *device;
  1149     SDL_bool build_stream;
  1150     void *handle = NULL;
  1151     int i = 0;
  1152 
  1153     if (!SDL_WasInit(SDL_INIT_AUDIO)) {
  1154         SDL_SetError("Audio subsystem is not initialized");
  1155         return 0;
  1156     }
  1157 
  1158     if ((iscapture) && (!current_audio.impl.HasCaptureSupport)) {
  1159         SDL_SetError("No capture support");
  1160         return 0;
  1161     }
  1162 
  1163     /* !!! FIXME: there is a race condition here if two devices open from two threads at once. */
  1164     /* Find an available device ID... */
  1165     for (id = min_id - 1; id < SDL_arraysize(open_devices); id++) {
  1166         if (open_devices[id] == NULL) {
  1167             break;
  1168         }
  1169     }
  1170 
  1171     if (id == SDL_arraysize(open_devices)) {
  1172         SDL_SetError("Too many open audio devices");
  1173         return 0;
  1174     }
  1175 
  1176     if (!obtained) {
  1177         obtained = &_obtained;
  1178     }
  1179     if (!prepare_audiospec(desired, obtained)) {
  1180         return 0;
  1181     }
  1182 
  1183     /* If app doesn't care about a specific device, let the user override. */
  1184     if (devname == NULL) {
  1185         devname = SDL_getenv("SDL_AUDIO_DEVICE_NAME");
  1186     }
  1187 
  1188     /*
  1189      * Catch device names at the high level for the simple case...
  1190      * This lets us have a basic "device enumeration" for systems that
  1191      *  don't have multiple devices, but makes sure the device name is
  1192      *  always NULL when it hits the low level.
  1193      *
  1194      * Also make sure that the simple case prevents multiple simultaneous
  1195      *  opens of the default system device.
  1196      */
  1197 
  1198     if ((iscapture) && (current_audio.impl.OnlyHasDefaultCaptureDevice)) {
  1199         if ((devname) && (SDL_strcmp(devname, DEFAULT_INPUT_DEVNAME) != 0)) {
  1200             SDL_SetError("No such device");
  1201             return 0;
  1202         }
  1203         devname = NULL;
  1204 
  1205         for (i = 0; i < SDL_arraysize(open_devices); i++) {
  1206             if ((open_devices[i]) && (open_devices[i]->iscapture)) {
  1207                 SDL_SetError("Audio device already open");
  1208                 return 0;
  1209             }
  1210         }
  1211     } else if ((!iscapture) && (current_audio.impl.OnlyHasDefaultOutputDevice)) {
  1212         if ((devname) && (SDL_strcmp(devname, DEFAULT_OUTPUT_DEVNAME) != 0)) {
  1213             SDL_SetError("No such device");
  1214             return 0;
  1215         }
  1216         devname = NULL;
  1217 
  1218         for (i = 0; i < SDL_arraysize(open_devices); i++) {
  1219             if ((open_devices[i]) && (!open_devices[i]->iscapture)) {
  1220                 SDL_SetError("Audio device already open");
  1221                 return 0;
  1222             }
  1223         }
  1224     } else if (devname != NULL) {
  1225         /* if the app specifies an exact string, we can pass the backend
  1226            an actual device handle thingey, which saves them the effort of
  1227            figuring out what device this was (such as, reenumerating
  1228            everything again to find the matching human-readable name).
  1229            It might still need to open a device based on the string for,
  1230            say, a network audio server, but this optimizes some cases. */
  1231         SDL_AudioDeviceItem *item;
  1232         SDL_LockMutex(current_audio.detectionLock);
  1233         for (item = iscapture ? current_audio.inputDevices : current_audio.outputDevices; item; item = item->next) {
  1234             if ((item->handle != NULL) && (SDL_strcmp(item->name, devname) == 0)) {
  1235                 handle = item->handle;
  1236                 break;
  1237             }
  1238         }
  1239         SDL_UnlockMutex(current_audio.detectionLock);
  1240     }
  1241 
  1242     if (!current_audio.impl.AllowsArbitraryDeviceNames) {
  1243         /* has to be in our device list, or the default device. */
  1244         if ((handle == NULL) && (devname != NULL)) {
  1245             SDL_SetError("No such device.");
  1246             return 0;
  1247         }
  1248     }
  1249 
  1250     device = (SDL_AudioDevice *) SDL_calloc(1, sizeof (SDL_AudioDevice));
  1251     if (device == NULL) {
  1252         SDL_OutOfMemory();
  1253         return 0;
  1254     }
  1255     device->id = id + 1;
  1256     device->spec = *obtained;
  1257     device->iscapture = iscapture ? SDL_TRUE : SDL_FALSE;
  1258     device->handle = handle;
  1259 
  1260     SDL_AtomicSet(&device->shutdown, 0);  /* just in case. */
  1261     SDL_AtomicSet(&device->paused, 1);
  1262     SDL_AtomicSet(&device->enabled, 1);
  1263 
  1264     /* Create a mutex for locking the sound buffers */
  1265     if (!current_audio.impl.SkipMixerLock) {
  1266         device->mixer_lock = SDL_CreateMutex();
  1267         if (device->mixer_lock == NULL) {
  1268             close_audio_device(device);
  1269             SDL_SetError("Couldn't create mixer lock");
  1270             return 0;
  1271         }
  1272     }
  1273 
  1274     if (current_audio.impl.OpenDevice(device, handle, devname, iscapture) < 0) {
  1275         close_audio_device(device);
  1276         return 0;
  1277     }
  1278 
  1279     /* if your target really doesn't need it, set it to 0x1 or something. */
  1280     /* otherwise, close_audio_device() won't call impl.CloseDevice(). */
  1281     SDL_assert(device->hidden != NULL);
  1282 
  1283     /* See if we need to do any conversion */
  1284     build_stream = SDL_FALSE;
  1285     if (obtained->freq != device->spec.freq) {
  1286         if (allowed_changes & SDL_AUDIO_ALLOW_FREQUENCY_CHANGE) {
  1287             obtained->freq = device->spec.freq;
  1288         } else {
  1289             build_stream = SDL_TRUE;
  1290         }
  1291     }
  1292     if (obtained->format != device->spec.format) {
  1293         if (allowed_changes & SDL_AUDIO_ALLOW_FORMAT_CHANGE) {
  1294             obtained->format = device->spec.format;
  1295         } else {
  1296             build_stream = SDL_TRUE;
  1297         }
  1298     }
  1299     if (obtained->channels != device->spec.channels) {
  1300         if (allowed_changes & SDL_AUDIO_ALLOW_CHANNELS_CHANGE) {
  1301             obtained->channels = device->spec.channels;
  1302         } else {
  1303             build_stream = SDL_TRUE;
  1304         }
  1305     }
  1306 
  1307     /* !!! FIXME in 2.1: add SDL_AUDIO_ALLOW_SAMPLES_CHANGE flag?
  1308        As of 2.0.6, we will build a stream to buffer the difference between
  1309        what the app wants to feed and the device wants to eat, so everyone
  1310        gets their way. In prior releases, SDL would force the callback to
  1311        feed at the rate the device requested, adjusted for resampling.
  1312      */
  1313     if (device->spec.samples != obtained->samples) {
  1314         build_stream = SDL_TRUE;
  1315     }
  1316 
  1317     SDL_CalculateAudioSpec(obtained);  /* recalc after possible changes. */
  1318 
  1319     device->callbackspec = *obtained;
  1320 
  1321     if (build_stream) {
  1322         if (iscapture) {
  1323             device->stream = SDL_NewAudioStream(device->spec.format,
  1324                                   device->spec.channels, device->spec.freq,
  1325                                   obtained->format, obtained->channels, obtained->freq);
  1326         } else {
  1327             device->stream = SDL_NewAudioStream(obtained->format, obtained->channels,
  1328                                   obtained->freq, device->spec.format,
  1329                                   device->spec.channels, device->spec.freq);
  1330         }
  1331 
  1332         if (!device->stream) {
  1333             close_audio_device(device);
  1334             return 0;
  1335         }
  1336     }
  1337 
  1338     if (device->spec.callback == NULL) {  /* use buffer queueing? */
  1339         /* pool a few packets to start. Enough for two callbacks. */
  1340         device->buffer_queue = SDL_NewDataQueue(SDL_AUDIOBUFFERQUEUE_PACKETLEN, obtained->size * 2);
  1341         if (!device->buffer_queue) {
  1342             close_audio_device(device);
  1343             SDL_SetError("Couldn't create audio buffer queue");
  1344             return 0;
  1345         }
  1346         device->spec.callback = iscapture ? SDL_BufferQueueFillCallback : SDL_BufferQueueDrainCallback;
  1347         device->spec.userdata = device;
  1348     }
  1349 
  1350     /* Allocate a scratch audio buffer */
  1351     device->work_buffer_len = build_stream ? device->callbackspec.size : 0;
  1352     if (device->spec.size > device->work_buffer_len) {
  1353         device->work_buffer_len = device->spec.size;
  1354     }
  1355     SDL_assert(device->work_buffer_len > 0);
  1356 
  1357     device->work_buffer = (Uint8 *) SDL_malloc(device->work_buffer_len);
  1358     if (device->work_buffer == NULL) {
  1359         close_audio_device(device);
  1360         SDL_OutOfMemory();
  1361         return 0;
  1362     }
  1363 
  1364     open_devices[id] = device;  /* add it to our list of open devices. */
  1365 
  1366     /* Start the audio thread if necessary */
  1367     if (!current_audio.impl.ProvidesOwnCallbackThread) {
  1368         /* Start the audio thread */
  1369         /* !!! FIXME: we don't force the audio thread stack size here if it calls into user code, but maybe we should? */
  1370         /* buffer queueing callback only needs a few bytes, so make the stack tiny. */
  1371         const size_t stacksize = is_internal_thread ? 64 * 1024 : 0;
  1372         char threadname[64];
  1373 
  1374         SDL_snprintf(threadname, sizeof (threadname), "SDLAudioDev%d", (int) device->id);
  1375         device->thread = SDL_CreateThreadInternal(iscapture ? SDL_CaptureAudio : SDL_RunAudio, threadname, stacksize, device);
  1376 
  1377         if (device->thread == NULL) {
  1378             close_audio_device(device);
  1379             SDL_SetError("Couldn't create audio thread");
  1380             return 0;
  1381         }
  1382     }
  1383 
  1384     return device->id;
  1385 }
  1386 
  1387 
  1388 int
  1389 SDL_OpenAudio(SDL_AudioSpec * desired, SDL_AudioSpec * obtained)
  1390 {
  1391     SDL_AudioDeviceID id = 0;
  1392 
  1393     /* Start up the audio driver, if necessary. This is legacy behaviour! */
  1394     if (!SDL_WasInit(SDL_INIT_AUDIO)) {
  1395         if (SDL_InitSubSystem(SDL_INIT_AUDIO) < 0) {
  1396             return -1;
  1397         }
  1398     }
  1399 
  1400     /* SDL_OpenAudio() is legacy and can only act on Device ID #1. */
  1401     if (open_devices[0] != NULL) {
  1402         SDL_SetError("Audio device is already opened");
  1403         return -1;
  1404     }
  1405 
  1406     if (obtained) {
  1407         id = open_audio_device(NULL, 0, desired, obtained,
  1408                                SDL_AUDIO_ALLOW_ANY_CHANGE, 1);
  1409     } else {
  1410         id = open_audio_device(NULL, 0, desired, NULL, 0, 1);
  1411     }
  1412 
  1413     SDL_assert((id == 0) || (id == 1));
  1414     return (id == 0) ? -1 : 0;
  1415 }
  1416 
  1417 SDL_AudioDeviceID
  1418 SDL_OpenAudioDevice(const char *device, int iscapture,
  1419                     const SDL_AudioSpec * desired, SDL_AudioSpec * obtained,
  1420                     int allowed_changes)
  1421 {
  1422     return open_audio_device(device, iscapture, desired, obtained,
  1423                              allowed_changes, 2);
  1424 }
  1425 
  1426 SDL_AudioStatus
  1427 SDL_GetAudioDeviceStatus(SDL_AudioDeviceID devid)
  1428 {
  1429     SDL_AudioDevice *device = get_audio_device(devid);
  1430     SDL_AudioStatus status = SDL_AUDIO_STOPPED;
  1431     if (device && SDL_AtomicGet(&device->enabled)) {
  1432         if (SDL_AtomicGet(&device->paused)) {
  1433             status = SDL_AUDIO_PAUSED;
  1434         } else {
  1435             status = SDL_AUDIO_PLAYING;
  1436         }
  1437     }
  1438     return status;
  1439 }
  1440 
  1441 
  1442 SDL_AudioStatus
  1443 SDL_GetAudioStatus(void)
  1444 {
  1445     return SDL_GetAudioDeviceStatus(1);
  1446 }
  1447 
  1448 void
  1449 SDL_PauseAudioDevice(SDL_AudioDeviceID devid, int pause_on)
  1450 {
  1451     SDL_AudioDevice *device = get_audio_device(devid);
  1452     if (device) {
  1453         current_audio.impl.LockDevice(device);
  1454         SDL_AtomicSet(&device->paused, pause_on ? 1 : 0);
  1455         current_audio.impl.UnlockDevice(device);
  1456     }
  1457 }
  1458 
  1459 void
  1460 SDL_PauseAudio(int pause_on)
  1461 {
  1462     SDL_PauseAudioDevice(1, pause_on);
  1463 }
  1464 
  1465 
  1466 void
  1467 SDL_LockAudioDevice(SDL_AudioDeviceID devid)
  1468 {
  1469     /* Obtain a lock on the mixing buffers */
  1470     SDL_AudioDevice *device = get_audio_device(devid);
  1471     if (device) {
  1472         current_audio.impl.LockDevice(device);
  1473     }
  1474 }
  1475 
  1476 void
  1477 SDL_LockAudio(void)
  1478 {
  1479     SDL_LockAudioDevice(1);
  1480 }
  1481 
  1482 void
  1483 SDL_UnlockAudioDevice(SDL_AudioDeviceID devid)
  1484 {
  1485     /* Obtain a lock on the mixing buffers */
  1486     SDL_AudioDevice *device = get_audio_device(devid);
  1487     if (device) {
  1488         current_audio.impl.UnlockDevice(device);
  1489     }
  1490 }
  1491 
  1492 void
  1493 SDL_UnlockAudio(void)
  1494 {
  1495     SDL_UnlockAudioDevice(1);
  1496 }
  1497 
  1498 void
  1499 SDL_CloseAudioDevice(SDL_AudioDeviceID devid)
  1500 {
  1501     close_audio_device(get_audio_device(devid));
  1502 }
  1503 
  1504 void
  1505 SDL_CloseAudio(void)
  1506 {
  1507     SDL_CloseAudioDevice(1);
  1508 }
  1509 
  1510 void
  1511 SDL_AudioQuit(void)
  1512 {
  1513     SDL_AudioDeviceID i;
  1514 
  1515     if (!current_audio.name) {  /* not initialized?! */
  1516         return;
  1517     }
  1518 
  1519     for (i = 0; i < SDL_arraysize(open_devices); i++) {
  1520         close_audio_device(open_devices[i]);
  1521     }
  1522 
  1523     free_device_list(&current_audio.outputDevices, &current_audio.outputDeviceCount);
  1524     free_device_list(&current_audio.inputDevices, &current_audio.inputDeviceCount);
  1525 
  1526     /* Free the driver data */
  1527     current_audio.impl.Deinitialize();
  1528 
  1529     SDL_DestroyMutex(current_audio.detectionLock);
  1530 
  1531     SDL_zero(current_audio);
  1532     SDL_zero(open_devices);
  1533 
  1534 #ifdef HAVE_LIBSAMPLERATE_H
  1535     UnloadLibSampleRate();
  1536 #endif
  1537 }
  1538 
  1539 #define NUM_FORMATS 10
  1540 static int format_idx;
  1541 static int format_idx_sub;
  1542 static SDL_AudioFormat format_list[NUM_FORMATS][NUM_FORMATS] = {
  1543     {AUDIO_U8, AUDIO_S8, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB,
  1544      AUDIO_U16MSB, AUDIO_S32LSB, AUDIO_S32MSB, AUDIO_F32LSB, AUDIO_F32MSB},
  1545     {AUDIO_S8, AUDIO_U8, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB,
  1546      AUDIO_U16MSB, AUDIO_S32LSB, AUDIO_S32MSB, AUDIO_F32LSB, AUDIO_F32MSB},
  1547     {AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_S32LSB,
  1548      AUDIO_S32MSB, AUDIO_F32LSB, AUDIO_F32MSB, AUDIO_U8, AUDIO_S8},
  1549     {AUDIO_S16MSB, AUDIO_S16LSB, AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_S32MSB,
  1550      AUDIO_S32LSB, AUDIO_F32MSB, AUDIO_F32LSB, AUDIO_U8, AUDIO_S8},
  1551     {AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_S16LSB, AUDIO_S16MSB, AUDIO_S32LSB,
  1552      AUDIO_S32MSB, AUDIO_F32LSB, AUDIO_F32MSB, AUDIO_U8, AUDIO_S8},
  1553     {AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_S16MSB, AUDIO_S16LSB, AUDIO_S32MSB,
  1554      AUDIO_S32LSB, AUDIO_F32MSB, AUDIO_F32LSB, AUDIO_U8, AUDIO_S8},
  1555     {AUDIO_S32LSB, AUDIO_S32MSB, AUDIO_F32LSB, AUDIO_F32MSB, AUDIO_S16LSB,
  1556      AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_U8, AUDIO_S8},
  1557     {AUDIO_S32MSB, AUDIO_S32LSB, AUDIO_F32MSB, AUDIO_F32LSB, AUDIO_S16MSB,
  1558      AUDIO_S16LSB, AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_U8, AUDIO_S8},
  1559     {AUDIO_F32LSB, AUDIO_F32MSB, AUDIO_S32LSB, AUDIO_S32MSB, AUDIO_S16LSB,
  1560      AUDIO_S16MSB, AUDIO_U16LSB, AUDIO_U16MSB, AUDIO_U8, AUDIO_S8},
  1561     {AUDIO_F32MSB, AUDIO_F32LSB, AUDIO_S32MSB, AUDIO_S32LSB, AUDIO_S16MSB,
  1562      AUDIO_S16LSB, AUDIO_U16MSB, AUDIO_U16LSB, AUDIO_U8, AUDIO_S8},
  1563 };
  1564 
  1565 SDL_AudioFormat
  1566 SDL_FirstAudioFormat(SDL_AudioFormat format)
  1567 {
  1568     for (format_idx = 0; format_idx < NUM_FORMATS; ++format_idx) {
  1569         if (format_list[format_idx][0] == format) {
  1570             break;
  1571         }
  1572     }
  1573     format_idx_sub = 0;
  1574     return SDL_NextAudioFormat();
  1575 }
  1576 
  1577 SDL_AudioFormat
  1578 SDL_NextAudioFormat(void)
  1579 {
  1580     if ((format_idx == NUM_FORMATS) || (format_idx_sub == NUM_FORMATS)) {
  1581         return 0;
  1582     }
  1583     return format_list[format_idx][format_idx_sub++];
  1584 }
  1585 
  1586 void
  1587 SDL_CalculateAudioSpec(SDL_AudioSpec * spec)
  1588 {
  1589     switch (spec->format) {
  1590     case AUDIO_U8:
  1591         spec->silence = 0x80;
  1592         break;
  1593     default:
  1594         spec->silence = 0x00;
  1595         break;
  1596     }
  1597     spec->size = SDL_AUDIO_BITSIZE(spec->format) / 8;
  1598     spec->size *= spec->channels;
  1599     spec->size *= spec->samples;
  1600 }
  1601 
  1602 
  1603 /*
  1604  * Moved here from SDL_mixer.c, since it relies on internals of an opened
  1605  *  audio device (and is deprecated, by the way!).
  1606  */
  1607 void
  1608 SDL_MixAudio(Uint8 * dst, const Uint8 * src, Uint32 len, int volume)
  1609 {
  1610     /* Mix the user-level audio format */
  1611     SDL_AudioDevice *device = get_audio_device(1);
  1612     if (device != NULL) {
  1613         SDL_MixAudioFormat(dst, src, device->callbackspec.format, len, volume);
  1614     }
  1615 }
  1616 
  1617 /* vi: set ts=4 sw=4 expandtab: */