summaryrefslogtreecommitdiffstatshomepage
path: root/3rdparty/SDL2/src/audio/winmm/SDL_winmm.c
diff options
context:
space:
mode:
Diffstat (limited to '3rdparty/SDL2/src/audio/winmm/SDL_winmm.c')
-rw-r--r--3rdparty/SDL2/src/audio/winmm/SDL_winmm.c423
1 files changed, 0 insertions, 423 deletions
diff --git a/3rdparty/SDL2/src/audio/winmm/SDL_winmm.c b/3rdparty/SDL2/src/audio/winmm/SDL_winmm.c
deleted file mode 100644
index 34f543ddb33..00000000000
--- a/3rdparty/SDL2/src/audio/winmm/SDL_winmm.c
+++ /dev/null
@@ -1,423 +0,0 @@
-/*
- Simple DirectMedia Layer
- Copyright (C) 1997-2016 Sam Lantinga <slouken@libsdl.org>
-
- This software is provided 'as-is', without any express or implied
- warranty. In no event will the authors be held liable for any damages
- arising from the use of this software.
-
- Permission is granted to anyone to use this software for any purpose,
- including commercial applications, and to alter it and redistribute it
- freely, subject to the following restrictions:
-
- 1. The origin of this software must not be misrepresented; you must not
- claim that you wrote the original software. If you use this software
- in a product, an acknowledgment in the product documentation would be
- appreciated but is not required.
- 2. Altered source versions must be plainly marked as such, and must not be
- misrepresented as being the original software.
- 3. This notice may not be removed or altered from any source distribution.
-*/
-#include "../../SDL_internal.h"
-
-#if SDL_AUDIO_DRIVER_WINMM
-
-/* Allow access to a raw mixing buffer */
-
-#include "../../core/windows/SDL_windows.h"
-#include <mmsystem.h>
-
-#include "SDL_assert.h"
-#include "SDL_timer.h"
-#include "SDL_audio.h"
-#include "../SDL_audio_c.h"
-#include "SDL_winmm.h"
-
-#ifndef WAVE_FORMAT_IEEE_FLOAT
-#define WAVE_FORMAT_IEEE_FLOAT 0x0003
-#endif
-
-#define DETECT_DEV_IMPL(iscap, typ, capstyp) \
-static void DetectWave##typ##Devs(void) { \
- const UINT iscapture = iscap ? 1 : 0; \
- const UINT devcount = wave##typ##GetNumDevs(); \
- capstyp##2W caps; \
- UINT i; \
- for (i = 0; i < devcount; i++) { \
- if (wave##typ##GetDevCaps(i,(LP##capstyp##W)&caps,sizeof(caps))==MMSYSERR_NOERROR) { \
- char *name = WIN_LookupAudioDeviceName(caps.szPname,&caps.NameGuid); \
- if (name != NULL) { \
- SDL_AddAudioDevice((int) iscapture, name, (void *) ((size_t) i+1)); \
- SDL_free(name); \
- } \
- } \
- } \
-}
-
-DETECT_DEV_IMPL(SDL_FALSE, Out, WAVEOUTCAPS)
-DETECT_DEV_IMPL(SDL_TRUE, In, WAVEINCAPS)
-
-static void
-WINMM_DetectDevices(void)
-{
- DetectWaveInDevs();
- DetectWaveOutDevs();
-}
-
-static void CALLBACK
-CaptureSound(HWAVEIN hwi, UINT uMsg, DWORD_PTR dwInstance,
- DWORD_PTR dwParam1, DWORD_PTR dwParam2)
-{
- SDL_AudioDevice *this = (SDL_AudioDevice *) dwInstance;
-
- /* Only service "buffer is filled" messages */
- if (uMsg != WIM_DATA)
- return;
-
- /* Signal that we have a new buffer of data */
- ReleaseSemaphore(this->hidden->audio_sem, 1, NULL);
-}
-
-
-/* The Win32 callback for filling the WAVE device */
-static void CALLBACK
-FillSound(HWAVEOUT hwo, UINT uMsg, DWORD_PTR dwInstance,
- DWORD_PTR dwParam1, DWORD_PTR dwParam2)
-{
- SDL_AudioDevice *this = (SDL_AudioDevice *) dwInstance;
-
- /* Only service "buffer done playing" messages */
- if (uMsg != WOM_DONE)
- return;
-
- /* Signal that we are done playing a buffer */
- ReleaseSemaphore(this->hidden->audio_sem, 1, NULL);
-}
-
-static int
-SetMMerror(char *function, MMRESULT code)
-{
- int len;
- char errbuf[MAXERRORLENGTH];
- wchar_t werrbuf[MAXERRORLENGTH];
-
- SDL_snprintf(errbuf, SDL_arraysize(errbuf), "%s: ", function);
- len = SDL_static_cast(int, SDL_strlen(errbuf));
-
- waveOutGetErrorText(code, werrbuf, MAXERRORLENGTH - len);
- WideCharToMultiByte(CP_ACP, 0, werrbuf, -1, errbuf + len,
- MAXERRORLENGTH - len, NULL, NULL);
-
- return SDL_SetError("%s", errbuf);
-}
-
-static void
-WINMM_WaitDevice(_THIS)
-{
- /* Wait for an audio chunk to finish */
- WaitForSingleObject(this->hidden->audio_sem, INFINITE);
-}
-
-static Uint8 *
-WINMM_GetDeviceBuf(_THIS)
-{
- return (Uint8 *) (this->hidden->
- wavebuf[this->hidden->next_buffer].lpData);
-}
-
-static void
-WINMM_PlayDevice(_THIS)
-{
- /* Queue it up */
- waveOutWrite(this->hidden->hout,
- &this->hidden->wavebuf[this->hidden->next_buffer],
- sizeof(this->hidden->wavebuf[0]));
- this->hidden->next_buffer = (this->hidden->next_buffer + 1) % NUM_BUFFERS;
-}
-
-static int
-WINMM_CaptureFromDevice(_THIS, void *buffer, int buflen)
-{
- const int nextbuf = this->hidden->next_buffer;
- MMRESULT result;
-
- SDL_assert(buflen == this->spec.size);
-
- /* Wait for an audio chunk to finish */
- WaitForSingleObject(this->hidden->audio_sem, INFINITE);
-
- /* Copy it to caller's buffer... */
- SDL_memcpy(buffer, this->hidden->wavebuf[nextbuf].lpData, this->spec.size);
-
- /* requeue the buffer that just finished. */
- result = waveInAddBuffer(this->hidden->hin,
- &this->hidden->wavebuf[nextbuf],
- sizeof (this->hidden->wavebuf[nextbuf]));
- if (result != MMSYSERR_NOERROR) {
- return -1; /* uhoh! Disable the device. */
- }
-
- /* queue the next buffer in sequence, next time. */
- this->hidden->next_buffer = (nextbuf + 1) % NUM_BUFFERS;
- return this->spec.size;
-}
-
-static void
-WINMM_FlushCapture(_THIS)
-{
- /* Wait for an audio chunk to finish */
- if (WaitForSingleObject(this->hidden->audio_sem, 0) == WAIT_OBJECT_0) {
- const int nextbuf = this->hidden->next_buffer;
- /* requeue the buffer that just finished without reading from it. */
- waveInAddBuffer(this->hidden->hin,
- &this->hidden->wavebuf[nextbuf],
- sizeof (this->hidden->wavebuf[nextbuf]));
- this->hidden->next_buffer = (nextbuf + 1) % NUM_BUFFERS;
- }
-}
-
-static void
-WINMM_CloseDevice(_THIS)
-{
- int i;
-
- if (this->hidden->hout) {
- waveOutReset(this->hidden->hout);
-
- /* Clean up mixing buffers */
- for (i = 0; i < NUM_BUFFERS; ++i) {
- if (this->hidden->wavebuf[i].dwUser != 0xFFFF) {
- waveOutUnprepareHeader(this->hidden->hout,
- &this->hidden->wavebuf[i],
- sizeof (this->hidden->wavebuf[i]));
- }
- }
-
- waveOutClose(this->hidden->hout);
- }
-
- if (this->hidden->hin) {
- waveInReset(this->hidden->hin);
-
- /* Clean up mixing buffers */
- for (i = 0; i < NUM_BUFFERS; ++i) {
- if (this->hidden->wavebuf[i].dwUser != 0xFFFF) {
- waveInUnprepareHeader(this->hidden->hin,
- &this->hidden->wavebuf[i],
- sizeof (this->hidden->wavebuf[i]));
- }
- }
- waveInClose(this->hidden->hin);
- }
-
- if (this->hidden->audio_sem) {
- CloseHandle(this->hidden->audio_sem);
- }
-
- SDL_free(this->hidden->mixbuf);
- SDL_free(this->hidden);
-}
-
-static SDL_bool
-PrepWaveFormat(_THIS, UINT devId, WAVEFORMATEX *pfmt, const int iscapture)
-{
- SDL_zerop(pfmt);
-
- if (SDL_AUDIO_ISFLOAT(this->spec.format)) {
- pfmt->wFormatTag = WAVE_FORMAT_IEEE_FLOAT;
- } else {
- pfmt->wFormatTag = WAVE_FORMAT_PCM;
- }
- pfmt->wBitsPerSample = SDL_AUDIO_BITSIZE(this->spec.format);
-
- pfmt->nChannels = this->spec.channels;
- pfmt->nSamplesPerSec = this->spec.freq;
- pfmt->nBlockAlign = pfmt->nChannels * (pfmt->wBitsPerSample / 8);
- pfmt->nAvgBytesPerSec = pfmt->nSamplesPerSec * pfmt->nBlockAlign;
-
- if (iscapture) {
- return (waveInOpen(0, devId, pfmt, 0, 0, WAVE_FORMAT_QUERY) == 0);
- } else {
- return (waveOutOpen(0, devId, pfmt, 0, 0, WAVE_FORMAT_QUERY) == 0);
- }
-}
-
-static int
-WINMM_OpenDevice(_THIS, void *handle, const char *devname, int iscapture)
-{
- SDL_AudioFormat test_format = SDL_FirstAudioFormat(this->spec.format);
- int valid_datatype = 0;
- MMRESULT result;
- WAVEFORMATEX waveformat;
- UINT devId = WAVE_MAPPER; /* WAVE_MAPPER == choose system's default */
- UINT i;
-
- if (handle != NULL) { /* specific device requested? */
- /* -1 because we increment the original value to avoid NULL. */
- const size_t val = ((size_t) handle) - 1;
- devId = (UINT) val;
- }
-
- /* Initialize all variables that we clean on shutdown */
- this->hidden = (struct SDL_PrivateAudioData *)
- SDL_malloc((sizeof *this->hidden));
- if (this->hidden == NULL) {
- return SDL_OutOfMemory();
- }
- SDL_zerop(this->hidden);
-
- /* Initialize the wavebuf structures for closing */
- for (i = 0; i < NUM_BUFFERS; ++i)
- this->hidden->wavebuf[i].dwUser = 0xFFFF;
-
- if (this->spec.channels > 2)
- this->spec.channels = 2; /* !!! FIXME: is this right? */
-
- while ((!valid_datatype) && (test_format)) {
- switch (test_format) {
- case AUDIO_U8:
- case AUDIO_S16:
- case AUDIO_S32:
- case AUDIO_F32:
- this->spec.format = test_format;
- if (PrepWaveFormat(this, devId, &waveformat, iscapture)) {
- valid_datatype = 1;
- } else {
- test_format = SDL_NextAudioFormat();
- }
- break;
-
- default:
- test_format = SDL_NextAudioFormat();
- break;
- }
- }
-
- if (!valid_datatype) {
- return SDL_SetError("Unsupported audio format");
- }
-
- /* Update the fragment size as size in bytes */
- SDL_CalculateAudioSpec(&this->spec);
-
- /* Open the audio device */
- if (iscapture) {
- result = waveInOpen(&this->hidden->hin, devId, &waveformat,
- (DWORD_PTR) CaptureSound, (DWORD_PTR) this,
- CALLBACK_FUNCTION);
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveInOpen()", result);
- }
- } else {
- result = waveOutOpen(&this->hidden->hout, devId, &waveformat,
- (DWORD_PTR) FillSound, (DWORD_PTR) this,
- CALLBACK_FUNCTION);
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveOutOpen()", result);
- }
- }
-
-#ifdef SOUND_DEBUG
- /* Check the sound device we retrieved */
- {
- if (iscapture) {
- WAVEINCAPS caps;
- result = waveInGetDevCaps((UINT) this->hidden->hout,
- &caps, sizeof (caps));
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveInGetDevCaps()", result);
- }
- printf("Audio device: %s\n", caps.szPname);
- } else {
- WAVEOUTCAPS caps;
- result = waveOutGetDevCaps((UINT) this->hidden->hout,
- &caps, sizeof(caps));
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveOutGetDevCaps()", result);
- }
- printf("Audio device: %s\n", caps.szPname);
- }
- }
-#endif
-
- /* Create the audio buffer semaphore */
- this->hidden->audio_sem =
- CreateSemaphore(NULL, iscapture ? 0 : NUM_BUFFERS - 1, NUM_BUFFERS, NULL);
- if (this->hidden->audio_sem == NULL) {
- return SDL_SetError("Couldn't create semaphore");
- }
-
- /* Create the sound buffers */
- this->hidden->mixbuf =
- (Uint8 *) SDL_malloc(NUM_BUFFERS * this->spec.size);
- if (this->hidden->mixbuf == NULL) {
- return SDL_OutOfMemory();
- }
-
- SDL_zero(this->hidden->wavebuf);
- for (i = 0; i < NUM_BUFFERS; ++i) {
- this->hidden->wavebuf[i].dwBufferLength = this->spec.size;
- this->hidden->wavebuf[i].dwFlags = WHDR_DONE;
- this->hidden->wavebuf[i].lpData =
- (LPSTR) & this->hidden->mixbuf[i * this->spec.size];
-
- if (iscapture) {
- result = waveInPrepareHeader(this->hidden->hin,
- &this->hidden->wavebuf[i],
- sizeof(this->hidden->wavebuf[i]));
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveInPrepareHeader()", result);
- }
-
- result = waveInAddBuffer(this->hidden->hin,
- &this->hidden->wavebuf[i],
- sizeof(this->hidden->wavebuf[i]));
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveInAddBuffer()", result);
- }
- } else {
- result = waveOutPrepareHeader(this->hidden->hout,
- &this->hidden->wavebuf[i],
- sizeof(this->hidden->wavebuf[i]));
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveOutPrepareHeader()", result);
- }
- }
- }
-
- if (iscapture) {
- result = waveInStart(this->hidden->hin);
- if (result != MMSYSERR_NOERROR) {
- return SetMMerror("waveInStart()", result);
- }
- }
-
- return 0; /* Ready to go! */
-}
-
-
-static int
-WINMM_Init(SDL_AudioDriverImpl * impl)
-{
- /* Set the function pointers */
- impl->DetectDevices = WINMM_DetectDevices;
- impl->OpenDevice = WINMM_OpenDevice;
- impl->PlayDevice = WINMM_PlayDevice;
- impl->WaitDevice = WINMM_WaitDevice;
- impl->GetDeviceBuf = WINMM_GetDeviceBuf;
- impl->CaptureFromDevice = WINMM_CaptureFromDevice;
- impl->FlushCapture = WINMM_FlushCapture;
- impl->CloseDevice = WINMM_CloseDevice;
-
- impl->HasCaptureSupport = SDL_TRUE;
-
- return 1; /* this audio target is available. */
-}
-
-AudioBootStrap WINMM_bootstrap = {
- "winmm", "Windows Waveform Audio", WINMM_Init, 0
-};
-
-#endif /* SDL_AUDIO_DRIVER_WINMM */
-
-/* vi: set ts=4 sw=4 expandtab: */