#include "SDL_internal.h"
#ifndef SDL_sysaudio_h_
#define SDL_sysaudio_h_
#define DEBUG_AUDIOSTREAM 0
#define DEBUG_AUDIO_CONVERT 0
#if DEBUG_AUDIO_CONVERT
#define LOG_DEBUG_AUDIO_CONVERT(from, to) SDL_Log("SDL_AUDIO_CONVERT: Converting %s to %s.", from, to);
#else
#define LOG_DEBUG_AUDIO_CONVERT(from, to)
#endif
#define DEFAULT_PLAYBACK_DEVNAME "System audio playback device"
#define DEFAULT_RECORDING_DEVNAME "System audio recording device"
#define DEFAULT_AUDIO_PLAYBACK_FORMAT SDL_AUDIO_S16
#define DEFAULT_AUDIO_PLAYBACK_CHANNELS 2
#define DEFAULT_AUDIO_PLAYBACK_FREQUENCY 44100
#define DEFAULT_AUDIO_RECORDING_FORMAT SDL_AUDIO_S16
#define DEFAULT_AUDIO_RECORDING_CHANNELS 1
#define DEFAULT_AUDIO_RECORDING_FREQUENCY 44100
#define SDL_MAX_CHANNELMAP_CHANNELS 8
typedef struct SDL_AudioDevice SDL_AudioDevice;
typedef struct SDL_LogicalAudioDevice SDL_LogicalAudioDevice;
extern bool SDL_InitAudio(const char *driver_name);
extern void SDL_QuitAudio(void);
const SDL_AudioFormat *SDL_ClosestAudioFormats(SDL_AudioFormat format);
extern void SDL_ChooseAudioConverters(void);
extern void SDL_SetupAudioResampler(void);
extern SDL_AudioDevice *SDL_AddAudioDevice(bool recording, const char *name, const SDL_AudioSpec *spec, void *handle);
extern void SDL_AudioDeviceDisconnected(SDL_AudioDevice *device);
extern void SDL_DefaultAudioDeviceChanged(SDL_AudioDevice *new_default_device);
extern bool SDL_AudioDeviceFormatChanged(SDL_AudioDevice *device, const SDL_AudioSpec *newspec, int new_sample_frames);
extern bool SDL_AudioDeviceFormatChangedAlreadyLocked(SDL_AudioDevice *device, const SDL_AudioSpec *newspec, int new_sample_frames);
extern SDL_AudioDevice *SDL_FindPhysicalAudioDeviceByHandle(void *handle);
extern SDL_AudioDevice *SDL_FindPhysicalAudioDeviceByCallback(bool (*callback)(SDL_AudioDevice *device, void *userdata), void *userdata);
extern void SDL_UpdatedAudioDeviceFormat(SDL_AudioDevice *device);
int SDL_GetDefaultSampleFramesFromFreq(const int freq);
extern char *SDL_GetAudioThreadName(SDL_AudioDevice *device, char *buf, size_t buflen);
extern void RefPhysicalAudioDevice(SDL_AudioDevice *device);
extern void UnrefPhysicalAudioDevice(SDL_AudioDevice *device);
extern void SDL_PlaybackAudioThreadSetup(SDL_AudioDevice *device);
extern bool SDL_PlaybackAudioThreadIterate(SDL_AudioDevice *device);
extern void SDL_PlaybackAudioThreadShutdown(SDL_AudioDevice *device);
extern void SDL_RecordingAudioThreadSetup(SDL_AudioDevice *device);
extern bool SDL_RecordingAudioThreadIterate(SDL_AudioDevice *device);
extern void SDL_RecordingAudioThreadShutdown(SDL_AudioDevice *device);
extern void SDL_AudioThreadFinalize(SDL_AudioDevice *device);
extern void ConvertAudioToFloat(float *dst, const void *src, int num_samples, SDL_AudioFormat src_fmt);
extern void ConvertAudioFromFloat(void *dst, const float *src, int num_samples, SDL_AudioFormat dst_fmt);
extern void ConvertAudioSwapEndian(void *dst, const void *src, int num_samples, int bitsize);
extern bool SDL_ChannelMapIsDefault(const int *map, int channels);
extern bool SDL_ChannelMapIsBogus(const int *map, int channels);
extern void ConvertAudio(int num_frames,
const void *src, SDL_AudioFormat src_format, int src_channels, const int *src_map,
void *dst, SDL_AudioFormat dst_format, int dst_channels, const int *dst_map,
void *scratch, float gain);
extern bool SDL_AudioSpecsEqual(const SDL_AudioSpec *a, const SDL_AudioSpec *b, const int *channel_map_a, const int *channel_map_b);
extern bool SDL_AudioChannelMapsEqual(int channels, const int *channel_map_a, const int *channel_map_b);
extern int *SDL_ChannelMapDup(const int *origchmap, int channels);
extern void OnAudioStreamCreated(SDL_AudioStream *stream);
extern void OnAudioStreamDestroy(SDL_AudioStream *stream);
extern int SDL_GetAudioStreamDataAdjustGain(SDL_AudioStream *stream, void *voidbuf, int len, float extra_gain);
extern bool SetAudioStreamChannelMap(SDL_AudioStream *stream, const SDL_AudioSpec *spec, int **stream_chmap, const int *chmap, int channels, int isinput);
typedef struct SDL_AudioDriverImpl
{
void (*DetectDevices)(SDL_AudioDevice **default_playback, SDL_AudioDevice **default_recording);
bool (*OpenDevice)(SDL_AudioDevice *device);
void (*ThreadInit)(SDL_AudioDevice *device); void (*ThreadDeinit)(SDL_AudioDevice *device); bool (*WaitDevice)(SDL_AudioDevice *device);
bool (*PlayDevice)(SDL_AudioDevice *device, const Uint8 *buffer, int buflen); Uint8 *(*GetDeviceBuf)(SDL_AudioDevice *device, int *buffer_size);
bool (*WaitRecordingDevice)(SDL_AudioDevice *device);
int (*RecordDevice)(SDL_AudioDevice *device, void *buffer, int buflen);
void (*FlushRecording)(SDL_AudioDevice *device);
void (*CloseDevice)(SDL_AudioDevice *device);
void (*FreeDeviceHandle)(SDL_AudioDevice *device); void (*DeinitializeStart)(void); void (*Deinitialize)(void);
bool ProvidesOwnCallbackThread; bool HasRecordingSupport;
bool OnlyHasDefaultPlaybackDevice;
bool OnlyHasDefaultRecordingDevice; } SDL_AudioDriverImpl;
typedef struct SDL_PendingAudioDeviceEvent
{
Uint32 type;
SDL_AudioDeviceID devid;
struct SDL_PendingAudioDeviceEvent *next;
} SDL_PendingAudioDeviceEvent;
typedef struct SDL_AudioDriver
{
const char *name; const char *desc; SDL_AudioDriverImpl impl; SDL_RWLock *subsystem_rwlock; SDL_HashTable *device_hash_physical; SDL_HashTable *device_hash_logical; SDL_AudioStream *existing_streams; SDL_AudioDeviceID default_playback_device_id;
SDL_AudioDeviceID default_recording_device_id;
SDL_PendingAudioDeviceEvent pending_events;
SDL_PendingAudioDeviceEvent *pending_events_tail;
SDL_AtomicInt playback_device_count;
SDL_AtomicInt recording_device_count;
SDL_AtomicInt shutting_down; } SDL_AudioDriver;
struct SDL_AudioQueue;
struct SDL_AudioStream
{
SDL_Mutex *lock;
SDL_PropertiesID props;
SDL_AudioStreamCallback get_callback;
void *get_callback_userdata;
SDL_AudioStreamCallback put_callback;
void *put_callback_userdata;
SDL_AudioSpec src_spec;
SDL_AudioSpec dst_spec;
int *src_chmap;
int *dst_chmap;
float freq_ratio;
float gain;
struct SDL_AudioQueue *queue;
SDL_AudioSpec input_spec; int *input_chmap;
int input_chmap_storage[SDL_MAX_CHANNELMAP_CHANNELS]; Sint64 resample_offset;
Uint8 *work_buffer; size_t work_buffer_allocation;
bool simplified;
SDL_LogicalAudioDevice *bound_device;
SDL_AudioStream *next_binding;
SDL_AudioStream *prev_binding;
SDL_AudioStream *prev; SDL_AudioStream *next; };
struct SDL_LogicalAudioDevice
{
SDL_AudioDeviceID instance_id;
SDL_AudioDevice *physical_device;
SDL_AtomicInt paused;
float gain;
SDL_AudioStream *bound_streams;
bool opened_as_default;
bool simplified;
SDL_AudioPostmixCallback postmix;
void *postmix_userdata;
SDL_LogicalAudioDevice *next;
SDL_LogicalAudioDevice *prev;
};
struct SDL_AudioDevice
{
SDL_Mutex *lock;
SDL_Condition *close_cond;
SDL_AtomicInt refcount;
bool (*WaitDevice)(SDL_AudioDevice *device);
bool (*PlayDevice)(SDL_AudioDevice *device, const Uint8 *buffer, int buflen);
Uint8 *(*GetDeviceBuf)(SDL_AudioDevice *device, int *buffer_size);
bool (*WaitRecordingDevice)(SDL_AudioDevice *device);
int (*RecordDevice)(SDL_AudioDevice *device, void *buffer, int buflen);
void (*FlushRecording)(SDL_AudioDevice *device);
char *name;
SDL_AudioDeviceID instance_id;
void *handle;
SDL_AudioSpec spec;
int buffer_size;
int *chmap;
SDL_AudioSpec default_spec;
int sample_frames;
int silence_value;
SDL_AtomicInt shutdown;
SDL_AtomicInt zombie;
bool recording;
bool simple_copy;
Uint8 *work_buffer;
Uint8 *mix_buffer;
float *postmix_buffer;
int work_buffer_size;
SDL_Thread *thread;
bool currently_opened;
struct SDL_PrivateAudioData *hidden;
SDL_LogicalAudioDevice *logical_devices;
};
typedef struct AudioBootStrap
{
const char *name;
const char *desc;
bool (*init)(SDL_AudioDriverImpl *impl);
bool demand_only; bool is_preferred;
} AudioBootStrap;
extern AudioBootStrap PRIVATEAUDIO_bootstrap;
extern AudioBootStrap PIPEWIRE_PREFERRED_bootstrap;
extern AudioBootStrap PIPEWIRE_bootstrap;
extern AudioBootStrap PULSEAUDIO_bootstrap;
extern AudioBootStrap ALSA_bootstrap;
extern AudioBootStrap JACK_bootstrap;
extern AudioBootStrap SNDIO_bootstrap;
extern AudioBootStrap NETBSDAUDIO_bootstrap;
extern AudioBootStrap DSP_bootstrap;
extern AudioBootStrap WASAPI_bootstrap;
extern AudioBootStrap DSOUND_bootstrap;
extern AudioBootStrap WINMM_bootstrap;
extern AudioBootStrap HAIKUAUDIO_bootstrap;
extern AudioBootStrap COREAUDIO_bootstrap;
extern AudioBootStrap DISKAUDIO_bootstrap;
extern AudioBootStrap DUMMYAUDIO_bootstrap;
extern AudioBootStrap AAUDIO_bootstrap;
extern AudioBootStrap OPENSLES_bootstrap;
extern AudioBootStrap PS2AUDIO_bootstrap;
extern AudioBootStrap PSPAUDIO_bootstrap;
extern AudioBootStrap VITAAUD_bootstrap;
extern AudioBootStrap N3DSAUDIO_bootstrap;
extern AudioBootStrap NGAGEAUDIO_bootstrap;
extern AudioBootStrap EMSCRIPTENAUDIO_bootstrap;
extern AudioBootStrap QSAAUDIO_bootstrap;
#endif