From bb8f2fc023f51791e40db54416279e38cfb6fa23 Mon Sep 17 00:00:00 2001 From: jakemsr Date: Sun, 2 Nov 2008 14:53:51 +0000 Subject: [PATCH] add libsndio backend and use it by default. take maintainership as suggested by current maintainer. ok pvalchev@ --- devel/sdl/Makefile | 15 +- devel/sdl/files/SDL_libsndioaudio.c | 282 ++++++++++++++++++ devel/sdl/files/SDL_libsndioaudio.h | 61 ++++ devel/sdl/patches/patch-configure | 39 ++- .../sdl/patches/patch-include_SDL_config_h_in | 11 + devel/sdl/patches/patch-src_audio_SDL_audio_c | 22 +- .../patches/patch-src_audio_SDL_sysaudio_h | 13 + 7 files changed, 427 insertions(+), 16 deletions(-) create mode 100644 devel/sdl/files/SDL_libsndioaudio.c create mode 100644 devel/sdl/files/SDL_libsndioaudio.h create mode 100644 devel/sdl/patches/patch-include_SDL_config_h_in create mode 100644 devel/sdl/patches/patch-src_audio_SDL_sysaudio_h diff --git a/devel/sdl/Makefile b/devel/sdl/Makefile index 7a22db16bfd..9ccceebcc13 100644 --- a/devel/sdl/Makefile +++ b/devel/sdl/Makefile @@ -1,22 +1,22 @@ -# $OpenBSD: Makefile,v 1.66 2008/09/26 03:14:42 brad Exp $ +# $OpenBSD: Makefile,v 1.67 2008/11/02 14:53:51 jakemsr Exp $ COMMENT= cross-platform multimedia library VERSION= 1.2.13 DISTNAME= SDL-${VERSION} -PKGNAME= ${DISTNAME:L}p5 +PKGNAME= ${DISTNAME:L}p6 CATEGORIES= devel HOMEPAGE= http://www.libsdl.org/ -MAINTAINER= Peter Valchev +MAINTAINER= Jacob Meuser # LGPLv2.1+ PERMIT_PACKAGE_CDROM= Yes PERMIT_PACKAGE_FTP= Yes PERMIT_DISTFILES_CDROM= Yes PERMIT_DISTFILES_FTP= Yes -WANTLIB= m usbhid +WANTLIB= m sndio usbhid MASTER_SITES= ftp://ftp.fr.freebsd.org/pub/FreeBSD/distfiles/ \ ${HOMEPAGE}release/ @@ -39,7 +39,8 @@ MODGNU_CONFIG_GUESS_DIRS= ${WRKSRC} ${WRKSRC}/test SHARED_LIBS= SDL 8.0 CONFIGURE_ENV+= X11BASE="${X11BASE}" \ CFLAGS="${CFLAGS} -I${LOCALBASE}/include" \ - LDFLAGS="-L${LOCALBASE}/lib" + LDFLAGS="-L${LOCALBASE}/lib" \ + WITH_LIBSNDIO="Yes" # in case devel/usb is installed, don't pick it up. CONFIGURE_ENV+= ac_cv_lib_usb_hid_init=no \ @@ -105,4 +106,8 @@ CONFIGURE_ARGS+=--disable-altivec NO_REGRESS= Yes +pre-configure: + mkdir -p ${WRKSRC}/src/audio/libsndio + cp ${FILESDIR}/SDL_libsndioaudio.{c,h} ${WRKSRC}/src/audio/libsndio + .include diff --git a/devel/sdl/files/SDL_libsndioaudio.c b/devel/sdl/files/SDL_libsndioaudio.c new file mode 100644 index 00000000000..b60e92ed6dd --- /dev/null +++ b/devel/sdl/files/SDL_libsndioaudio.c @@ -0,0 +1,282 @@ +/* + SDL - Simple DirectMedia Layer + Copyright (C) 1997-2006 Sam Lantinga + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + + Sam Lantinga + slouken@libsdl.org +*/ +#include "SDL_config.h" + +/* Allow access to a raw mixing buffer */ + +#ifdef HAVE_SIGNAL_H +#include +#endif +#include + +#include "SDL_timer.h" +#include "SDL_audio.h" +#include "../SDL_audiomem.h" +#include "../SDL_audio_c.h" +#include "../SDL_audiodev_c.h" +#include "SDL_libsndioaudio.h" + +/* The tag name used by libsndio audio */ +#define LIBSNDIO_DRIVER_NAME "libsndio" + +/* Audio driver functions */ +static int LIBSNDIO_OpenAudio(_THIS, SDL_AudioSpec *spec); +static void LIBSNDIO_WaitAudio(_THIS); +static void LIBSNDIO_PlayAudio(_THIS); +static Uint8 *LIBSNDIO_GetAudioBuf(_THIS); +static void LIBSNDIO_CloseAudio(_THIS); + +/* Audio driver bootstrap functions */ + +static int Audio_Available(void) +{ + struct sio_hdl *this_hdl; + int available = 0; + + if ( (this_hdl = sio_open(NULL, SIO_PLAY, 0)) != NULL ) { + sio_close(this_hdl); + available = 1; + } + + return available; +} + +static void Audio_DeleteDevice(SDL_AudioDevice *device) +{ + SDL_free(device->hidden); + SDL_free(device); +} + +static SDL_AudioDevice *Audio_CreateDevice(int devindex) +{ + SDL_AudioDevice *this; + + /* Initialize all variables that we clean on shutdown */ + this = (SDL_AudioDevice *)SDL_malloc(sizeof(SDL_AudioDevice)); + if ( this ) { + SDL_memset(this, 0, (sizeof *this)); + this->hidden = (struct SDL_PrivateAudioData *) + SDL_malloc((sizeof *this->hidden)); + } + if ( (this == NULL) || (this->hidden == NULL) ) { + SDL_OutOfMemory(); + if ( this ) { + SDL_free(this); + } + return(0); + } + SDL_memset(this->hidden, 0, (sizeof *this->hidden)); + + /* Set the function pointers */ + this->OpenAudio = LIBSNDIO_OpenAudio; + this->WaitAudio = LIBSNDIO_WaitAudio; + this->PlayAudio = LIBSNDIO_PlayAudio; + this->GetAudioBuf = LIBSNDIO_GetAudioBuf; + this->CloseAudio = LIBSNDIO_CloseAudio; + + this->free = Audio_DeleteDevice; + + hdl = NULL; + + return this; +} + +AudioBootStrap LIBSNDIO_bootstrap = { + LIBSNDIO_DRIVER_NAME, "libsndio", + Audio_Available, Audio_CreateDevice +}; + + + +/* This function waits until it is possible to write a full sound buffer */ +static void LIBSNDIO_WaitAudio(_THIS) +{ + Sint32 ticks; + + /* Check to see if the thread-parent process is still alive */ + { static int cnt = 0; + /* Note that this only works with thread implementations + that use a different process id for each thread. + */ + if (parent && (((++cnt)%10) == 0)) { /* Check every 10 loops */ + if ( kill(parent, 0) < 0 ) { + this->enabled = 0; + } + } + } + + /* Use timer for general audio synchronization */ + ticks = ((Sint32)(next_frame - SDL_GetTicks()))-FUDGE_TICKS; + if ( ticks > 0 ) { + SDL_Delay(ticks); + } +} + +static void LIBSNDIO_PlayAudio(_THIS) +{ + int written; + + /* Write the audio data */ + written = sio_write(hdl, mixbuf, mixlen); + + /* If timer synchronization is enabled, set the next write frame */ + if ( frame_ticks ) { + next_frame += frame_ticks; + } + + /* If we couldn't write, assume fatal error for now */ + if ( written == 0 ) { + this->enabled = 0; + } +#ifdef DEBUG_AUDIO + fprintf(stderr, "Wrote %d bytes of audio data\n", written); +#endif +} + +static Uint8 *LIBSNDIO_GetAudioBuf(_THIS) +{ + return(mixbuf); +} + +static void LIBSNDIO_CloseAudio(_THIS) +{ + if ( mixbuf != NULL ) { + SDL_FreeAudioMem(mixbuf); + mixbuf = NULL; + } + if ( hdl != NULL ) { + sio_close(hdl); + hdl = NULL; + } +} + +static int LIBSNDIO_OpenAudio(_THIS, SDL_AudioSpec *spec) +{ + struct sio_par par; + + /* Reset the timer synchronization flag */ + frame_ticks = 0.0; + next_frame = 0; + + mixbuf = NULL; + + if ((hdl = sio_open(NULL, SIO_PLAY, 0)) == NULL) { + SDL_SetError("sio_open() failed"); + return(-1); + } + + sio_initpar(&par); + + switch (spec->format) { + case AUDIO_S16LSB: + par.bits = 16; + par.sig = 1; + par.le = 1; + break; + case AUDIO_U8: + par.bits = 8; + par.sig = 0; + break; + default: + SDL_SetError("LIBSNDIO unknown format"); + return(-1); + } + + par.rate = spec->freq; + par.pchan = spec->channels; + + /* Calculate the final parameters for this audio specification */ + SDL_CalculateAudioSpec(spec); + + /* bufsz is in frames, size is in bytes. they both are counts + of the total buffer size (total latency desired) */ + par.bufsz = spec->size / par.pchan / (par.bits / 8); + + if (sio_setpar(hdl, &par) == 0) { + SDL_SetError("sio_setpar() failed"); + return(-1); + } + + if (sio_getpar(hdl, &par) == 0) { + SDL_SetError("sio_getpar() failed"); + return(-1); + } + + /* if wanted rate not found, find a multiple/factor */ + if (par.rate != spec->freq) { + if ((par.rate > spec->freq && par.rate % spec->freq != 0) || + (par.rate < spec->freq && spec->freq % par.rate != 0)) { + if ((spec->freq < 44100 && 44100 % spec->freq == 0) || + (spec->freq > 44100 && spec->freq % 44100 == 0)) { + sio_initpar(&par); + par.rate = 44100; + if (sio_setpar(hdl, &par) == 0) { + SDL_SetError("sio_setpar() failed"); + return(-1); + } + } + } + } + + if (sio_getpar(hdl, &par) == 0) { + SDL_SetError("sio_getpar() failed"); + return(-1); + } + + if (par.bits == 16 && par.sig == 1 && par.le == 1) + spec->format = AUDIO_S16LSB; + else if (par.bits == 8 && par.sig == 0) + spec->format = AUDIO_U8; + else { + SDL_SetError("LIBSNDIO couldn't configure a suitable format"); + return(-1); + } + + spec->freq = par.rate; + spec->channels = par.pchan; + + /* tell SDL we want to write in par.round sized blocks */ + /* this is problematic for some applications, don't do it now. + maybe in SDL-1.3. + spec->size = par.bufsz * par.pchan * par.bps; + frame_ticks = (float)par.bufsz / par.rate; + */ + + /* Allocate mixing buffer */ + mixlen = spec->size; + mixbuf = (Uint8 *)SDL_AllocAudioMem(mixlen); + if ( mixbuf == NULL ) { + return(-1); + } + SDL_memset(mixbuf, spec->silence, spec->size); + + /* Get the parent process id (we're the parent of the audio thread) */ + parent = getpid(); + + if ( sio_start(hdl) == 0 ) { + SDL_SetError("sio_start() failed"); + return(-1); + } + + /* We're ready to rock and roll. :-) */ + return(0); +} diff --git a/devel/sdl/files/SDL_libsndioaudio.h b/devel/sdl/files/SDL_libsndioaudio.h new file mode 100644 index 00000000000..5f0f34f5199 --- /dev/null +++ b/devel/sdl/files/SDL_libsndioaudio.h @@ -0,0 +1,61 @@ +/* + SDL - Simple DirectMedia Layer + Copyright (C) 1997-2006 Sam Lantinga + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2.1 of the License, or (at your option) any later version. + + This library is distributed in the hope that it will be useful, + but WITHOUT ANY WARRANTY; without even the implied warranty of + MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA + + Sam Lantinga + slouken@libsdl.org +*/ +#include "SDL_config.h" + +#ifndef _SDL_libsndioaudio_h +#define _SDL_libsndioaudio_h + +#include + +#include "../SDL_sysaudio.h" + +/* Hidden "this" pointer for the video functions */ +#define _THIS SDL_AudioDevice *this + +struct SDL_PrivateAudioData { + /* The stream descriptor for the audio device */ + struct sio_hdl *hdl; + + /* The parent process id, to detect when application quits */ + pid_t parent; + + /* Raw mixing buffer */ + Uint8 *mixbuf; + int mixlen; + + /* Support for audio timing using a timer, in addition to select() */ + float frame_ticks; + float next_frame; +}; +#define FUDGE_TICKS 10 /* The scheduler overhead ticks per frame */ + +/* Old variable names */ +#define stream (this->hidden->stream) +#define parent (this->hidden->parent) +#define mixbuf (this->hidden->mixbuf) +#define mixlen (this->hidden->mixlen) +#define frame_ticks (this->hidden->frame_ticks) +#define next_frame (this->hidden->next_frame) +#define hdl (this->hidden->hdl) + +#endif /* _SDL_libsaaudio_h */ + diff --git a/devel/sdl/patches/patch-configure b/devel/sdl/patches/patch-configure index 62a24b3ac15..817255ff5ee 100644 --- a/devel/sdl/patches/patch-configure +++ b/devel/sdl/patches/patch-configure @@ -1,7 +1,28 @@ -$OpenBSD: patch-configure,v 1.17 2008/03/19 13:33:29 jakemsr Exp $ +$OpenBSD: patch-configure,v 1.18 2008/11/02 14:53:51 jakemsr Exp $ --- configure.orig Sun Dec 30 21:09:39 2007 -+++ configure Mon Feb 18 00:21:17 2008 -@@ -25578,7 +25578,7 @@ fi ++++ configure Mon Sep 22 20:13:46 2008 +@@ -25411,6 +25411,20 @@ _ACEOF + fi + } + ++ ++CheckLibsndio() ++{ ++ if [ x"$WITH_LIBSNDIO" = x"Yes" ]; then ++ ++ cat >>confdefs.h <<\_ACEOF ++#define SDL_AUDIO_DRIVER_LIBSNDIO 1 ++_ACEOF ++ SOURCES="$SOURCES $srcdir/src/audio/libsndio/*.c" ++ EXTRA_LDFLAGS="$EXTRA_LDFLAGS -lsndio" ++ fi ++} ++ ++ + CheckPulseAudio() + { + # Check whether --enable-pulseaudio was given. +@@ -25578,7 +25592,7 @@ fi : # arts isn't installed else ARTS_CFLAGS=`$ARTSCONFIG --cflags` @@ -10,7 +31,7 @@ $OpenBSD: patch-configure,v 1.17 2008/03/19 13:33:29 jakemsr Exp $ ARTS_PREFIX=`$ARTSCONFIG --arts-prefix` { echo "$as_me:$LINENO: checking for aRts development environment" >&5 echo $ECHO_N "checking for aRts development environment... $ECHO_C" >&6; } -@@ -26333,9 +26333,6 @@ echo "${ECHO_T}$CompileNASM_ret" >&6; } +@@ -26333,9 +26347,6 @@ echo "${ECHO_T}$CompileNASM_ret" >&6; } win32) NASMFLAGS="-f win32" ;; @@ -20,7 +41,15 @@ $OpenBSD: patch-configure,v 1.17 2008/03/19 13:33:29 jakemsr Exp $ macosx) NASMFLAGS="-f macho" ;; -@@ -33612,10 +33609,10 @@ _ACEOF +@@ -33577,6 +33588,7 @@ _ACEOF + CheckALSA + CheckARTSC + CheckESD ++ CheckLibsndio + CheckPulseAudio + CheckNAS + CheckX11 +@@ -33612,10 +33624,10 @@ _ACEOF ;; netbsd|openbsd) cat >>confdefs.h <<\_ACEOF diff --git a/devel/sdl/patches/patch-include_SDL_config_h_in b/devel/sdl/patches/patch-include_SDL_config_h_in new file mode 100644 index 00000000000..f2f56e0c5c3 --- /dev/null +++ b/devel/sdl/patches/patch-include_SDL_config_h_in @@ -0,0 +1,11 @@ +$OpenBSD: patch-include_SDL_config_h_in,v 1.1 2008/11/02 14:53:51 jakemsr Exp $ +--- include/SDL_config.h.in.orig Sun Dec 30 20:48:36 2007 ++++ include/SDL_config.h.in Sun Sep 21 10:32:49 2008 +@@ -182,6 +182,7 @@ + #undef SDL_AUDIO_DRIVER_QNXNTO + #undef SDL_AUDIO_DRIVER_SNDMGR + #undef SDL_AUDIO_DRIVER_SUNAUDIO ++#undef SDL_AUDIO_DRIVER_LIBSNDIO + #undef SDL_AUDIO_DRIVER_WAVEOUT + + /* Enable various cdrom drivers */ diff --git a/devel/sdl/patches/patch-src_audio_SDL_audio_c b/devel/sdl/patches/patch-src_audio_SDL_audio_c index a6f9449a3bc..2a0ee95cf0a 100644 --- a/devel/sdl/patches/patch-src_audio_SDL_audio_c +++ b/devel/sdl/patches/patch-src_audio_SDL_audio_c @@ -1,7 +1,17 @@ -$OpenBSD: patch-src_audio_SDL_audio_c,v 1.13 2008/03/19 13:33:29 jakemsr Exp $ +$OpenBSD: patch-src_audio_SDL_audio_c,v 1.14 2008/11/02 14:53:51 jakemsr Exp $ --- src/audio/SDL_audio.c.orig Sun Dec 30 20:47:59 2007 -+++ src/audio/SDL_audio.c Mon Feb 18 01:41:22 2008 -@@ -341,6 +341,7 @@ int SDL_AudioInit(const char *driver_name) ++++ src/audio/SDL_audio.c Sun Oct 26 19:32:21 2008 +@@ -36,6 +36,9 @@ + + /* Available audio drivers */ + static AudioBootStrap *bootstrap[] = { ++#if SDL_AUDIO_DRIVER_LIBSNDIO ++ &LIBSNDIO_bootstrap, ++#endif + #if SDL_AUDIO_DRIVER_BSD + &BSD_AUDIO_bootstrap, + #endif +@@ -341,6 +344,7 @@ int SDL_AudioInit(const char *driver_name) } #endif /* SDL_AUDIO_DRIVER_ESD */ if ( audio == NULL ) { @@ -9,7 +19,7 @@ $OpenBSD: patch-src_audio_SDL_audio_c,v 1.13 2008/03/19 13:33:29 jakemsr Exp $ if ( driver_name != NULL ) { #if 0 /* This will be replaced with a better driver selection API */ if ( SDL_strrchr(driver_name, ':') != NULL ) { -@@ -357,12 +358,16 @@ int SDL_AudioInit(const char *driver_name) +@@ -357,12 +361,16 @@ int SDL_AudioInit(const char *driver_name) } } else { for ( i=0; bootstrap[i]; ++i ) { @@ -31,7 +41,7 @@ $OpenBSD: patch-src_audio_SDL_audio_c,v 1.13 2008/03/19 13:33:29 jakemsr Exp $ } } if ( audio == NULL ) { -@@ -518,8 +523,9 @@ int SDL_OpenAudio(SDL_AudioSpec *desired, SDL_AudioSpe +@@ -518,8 +526,9 @@ int SDL_OpenAudio(SDL_AudioSpec *desired, SDL_AudioSpe /* See if we need to do any conversion */ if ( obtained != NULL ) { @@ -43,7 +53,7 @@ $OpenBSD: patch-src_audio_SDL_audio_c,v 1.13 2008/03/19 13:33:29 jakemsr Exp $ desired->format != audio->spec.format || desired->channels != audio->spec.channels ) { /* Build an audio conversion block */ -@@ -532,7 +538,7 @@ int SDL_OpenAudio(SDL_AudioSpec *desired, SDL_AudioSpe +@@ -532,7 +541,7 @@ int SDL_OpenAudio(SDL_AudioSpec *desired, SDL_AudioSpe return(-1); } if ( audio->convert.needed ) { diff --git a/devel/sdl/patches/patch-src_audio_SDL_sysaudio_h b/devel/sdl/patches/patch-src_audio_SDL_sysaudio_h new file mode 100644 index 00000000000..4b96449c0df --- /dev/null +++ b/devel/sdl/patches/patch-src_audio_SDL_sysaudio_h @@ -0,0 +1,13 @@ +$OpenBSD: patch-src_audio_SDL_sysaudio_h,v 1.4 2008/11/02 14:53:51 jakemsr Exp $ +--- src/audio/SDL_sysaudio.h.orig Sun Dec 30 20:47:59 2007 ++++ src/audio/SDL_sysaudio.h Sun Sep 21 10:34:09 2008 +@@ -103,6 +103,9 @@ typedef struct AudioBootStrap { + #if SDL_AUDIO_DRIVER_BSD + extern AudioBootStrap BSD_AUDIO_bootstrap; + #endif ++#if SDL_AUDIO_DRIVER_LIBSNDIO ++extern AudioBootStrap LIBSNDIO_bootstrap; ++#endif + #if SDL_AUDIO_DRIVER_PULSE + extern AudioBootStrap PULSE_bootstrap; + #endif