https://github.com/libsdl-org/SDL/commit/18906a32b88d213b49816b157ab72a9f14da1532
From 18906a32b88d213b49816b157ab72a9f14da1532 Mon Sep 17 00:00:00 2001
From: "Ryan C. Gordon" <[EMAIL REDACTED]>
Date: Wed, 5 Jul 2023 00:22:35 -0400
Subject: [PATCH] jack: First shot at updating for SDL3 audio API.
---
CMakeLists.txt | 1 -
src/audio/jack/SDL_jackaudio.c | 77 ++++++++++++++++++++--------------
2 files changed, 46 insertions(+), 32 deletions(-)
diff --git a/CMakeLists.txt b/CMakeLists.txt
index 0af3be552861..c74b19ee5d6e 100644
--- a/CMakeLists.txt
+++ b/CMakeLists.txt
@@ -353,7 +353,6 @@ set_option(SDL_CLANG_TIDY "Run clang-tidy static analysis" OFF)
set(SDL_VENDOR_INFO "" CACHE STRING "Vendor name and/or version to add to SDL_REVISION")
-set(SDL_JACK OFF)
set(SDL_SNDIO OFF)
cmake_dependent_option(SDL_SHARED "Build a shared version of the library" ${SDL_SHARED_DEFAULT} ${SDL_SHARED_AVAILABLE} OFF)
diff --git a/src/audio/jack/SDL_jackaudio.c b/src/audio/jack/SDL_jackaudio.c
index 60deac3a7a8f..36bfbb8e7385 100644
--- a/src/audio/jack/SDL_jackaudio.c
+++ b/src/audio/jack/SDL_jackaudio.c
@@ -136,7 +136,7 @@ static int load_jack_syms(void)
static void jackShutdownCallback(void *arg) /* JACK went away; device is lost. */
{
SDL_AudioDevice *_this = (SDL_AudioDevice *)arg;
- SDL_OpenedAudioDeviceDisconnected(_this);
+ SDL_AudioDeviceDisconnected(_this);
SDL_PostSemaphore(_this->hidden->iosem); /* unblock the SDL thread. */
}
@@ -149,12 +149,12 @@ static int jackProcessPlaybackCallback(jack_nframes_t nframes, void *arg)
SDL_AudioDevice *_this = (SDL_AudioDevice *)arg;
jack_port_t **ports = _this->hidden->sdlports;
const int total_channels = _this->spec.channels;
- const int total_frames = _this->spec.samples;
+ const int total_frames = _this->sample_frames;
int channelsi;
- if (!SDL_AtomicGet(&_this->enabled)) {
+ if (SDL_AtomicGet(&_this->shutdown)) {
/* silence the buffer to avoid repeats and corruption. */
- SDL_memset(_this->hidden->iobuffer, '\0', _this->spec.size);
+ SDL_memset(_this->hidden->iobuffer, _this->silence_value, _this->buffer_size);
}
for (channelsi = 0; channelsi < total_channels; channelsi++) {
@@ -176,14 +176,14 @@ static int jackProcessPlaybackCallback(jack_nframes_t nframes, void *arg)
/* This function waits until it is possible to write a full sound buffer */
static void JACK_WaitDevice(SDL_AudioDevice *_this)
{
- if (SDL_AtomicGet(&_this->enabled)) {
+ if (!SDL_AtomicGet(&_this->shutdown)) {
if (SDL_WaitSemaphore(_this->hidden->iosem) == -1) {
- SDL_OpenedAudioDeviceDisconnected(_this);
+ SDL_AudioDeviceDisconnected(_this);
}
}
}
-static Uint8 *JACK_GetDeviceBuf(SDL_AudioDevice *_this)
+static Uint8 *JACK_GetDeviceBuf(SDL_AudioDevice *_this, int *buffer_size)
{
return (Uint8 *)_this->hidden->iobuffer;
}
@@ -191,10 +191,10 @@ static Uint8 *JACK_GetDeviceBuf(SDL_AudioDevice *_this)
static int jackProcessCaptureCallback(jack_nframes_t nframes, void *arg)
{
SDL_AudioDevice *_this = (SDL_AudioDevice *)arg;
- if (SDL_AtomicGet(&_this->enabled)) {
+ if (!SDL_AtomicGet(&_this->shutdown)) {
jack_port_t **ports = _this->hidden->sdlports;
const int total_channels = _this->spec.channels;
- const int total_frames = _this->spec.samples;
+ const int total_frames = _this->sample_frames;
int channelsi;
for (channelsi = 0; channelsi < total_channels; channelsi++) {
@@ -216,7 +216,7 @@ static int jackProcessCaptureCallback(jack_nframes_t nframes, void *arg)
static int JACK_CaptureFromDevice(SDL_AudioDevice *_this, void *buffer, int buflen)
{
- SDL_assert(buflen == _this->spec.size); /* we always fill a full buffer. */
+ SDL_assert(buflen == _this->buffer_size); /* we always fill a full buffer. */
/* Wait for JACK to fill the iobuffer */
if (SDL_WaitSemaphore(_this->hidden->iosem) == -1) {
@@ -234,30 +234,46 @@ static void JACK_FlushCapture(SDL_AudioDevice *_this)
static void JACK_CloseDevice(SDL_AudioDevice *_this)
{
- if (_this->hidden->client) {
- JACK_jack_deactivate(_this->hidden->client);
-
- if (_this->hidden->sdlports) {
- const int channels = _this->spec.channels;
- int i;
- for (i = 0; i < channels; i++) {
- JACK_jack_port_unregister(_this->hidden->client, _this->hidden->sdlports[i]);
+ if (_this->hidden) {
+ if (_this->hidden->client) {
+ JACK_jack_deactivate(_this->hidden->client);
+
+ if (_this->hidden->sdlports) {
+ const int channels = _this->spec.channels;
+ int i;
+ for (i = 0; i < channels; i++) {
+ JACK_jack_port_unregister(_this->hidden->client, _this->hidden->sdlports[i]);
+ }
+ SDL_free(_this->hidden->sdlports);
}
- SDL_free(_this->hidden->sdlports);
+
+ JACK_jack_client_close(_this->hidden->client);
}
- JACK_jack_client_close(_this->hidden->client);
- }
+ if (_this->hidden->iosem) {
+ SDL_DestroySemaphore(_this->hidden->iosem);
+ }
- if (_this->hidden->iosem) {
- SDL_DestroySemaphore(_this->hidden->iosem);
+ SDL_free(_this->hidden->iobuffer);
+ SDL_free(_this->hidden);
}
+}
- SDL_free(_this->hidden->iobuffer);
- SDL_free(_this->hidden);
+// !!! FIXME: unify this (PulseAudio has a getAppName, Pipewire has a thing, etc
+static const char *GetJackAppName(void)
+{
+ const char *retval = SDL_GetHint(SDL_HINT_AUDIO_DEVICE_APP_NAME);
+ if (retval && *retval) {
+ return retval;
+ }
+ retval = SDL_GetHint(SDL_HINT_APP_NAME);
+ if (retval && *retval) {
+ return retval;
+ }
+ return "SDL Application";
}
-static int JACK_OpenDevice(SDL_AudioDevice *_this, const char *devname)
+static int JACK_OpenDevice(SDL_AudioDevice *_this)
{
/* Note that JACK uses "output" for capture devices (they output audio
data to us) and "input" for playback (we input audio data to them).
@@ -282,8 +298,7 @@ static int JACK_OpenDevice(SDL_AudioDevice *_this, const char *devname)
return SDL_OutOfMemory();
}
- /* !!! FIXME: we _still_ need an API to specify an app name */
- client = JACK_jack_client_open("SDL", JackNoStartServer, &status, NULL);
+ client = JACK_jack_client_open(GetJackAppName(), JackNoStartServer, &status, NULL);
_this->hidden->client = client;
if (client == NULL) {
return SDL_SetError("Can't open JACK client");
@@ -320,9 +335,9 @@ static int JACK_OpenDevice(SDL_AudioDevice *_this, const char *devname)
_this->spec.format = SDL_AUDIO_F32SYS;
_this->spec.freq = JACK_jack_get_sample_rate(client);
_this->spec.channels = channels;
- _this->spec.samples = JACK_jack_get_buffer_size(client);
+ _this->sample_frames = JACK_jack_get_buffer_size(client);
- SDL_CalculateAudioSpec(&_this->spec);
+ SDL_UpdatedAudioDeviceFormat(_this);
_this->hidden->iosem = SDL_CreateSemaphore(0);
if (!_this->hidden->iosem) {
@@ -330,7 +345,7 @@ static int JACK_OpenDevice(SDL_AudioDevice *_this, const char *devname)
return -1; /* error was set by SDL_CreateSemaphore */
}
- _this->hidden->iobuffer = (float *)SDL_calloc(1, _this->spec.size);
+ _this->hidden->iobuffer = (float *)SDL_calloc(1, _this->buffer_size);
if (!_this->hidden->iobuffer) {
SDL_free(audio_ports);
return SDL_OutOfMemory();