Commit 98233844 authored by Sam Lantinga's avatar Sam Lantinga

Added an audio driver that writes to disk (thanks Ryan!)

--HG--
extra : convert_revision : svn%3Ac70aab31-4412-0410-b14c-859654838e24/trunk%4069
parent 9a765af0
......@@ -368,6 +368,21 @@ CheckNAS()
fi
}
dnl rcg07142001 See if the user wants the disk writer audio driver...
CheckDiskAudio()
{
AC_ARG_ENABLE(diskaudio,
[ --enable-diskaudio support the disk writer audio driver [default=no]],
, enable_diskaudio=no)
if test x$enable_audio = xyes -a x$enable_diskaudio = xyes; then
CFLAGS="$CFLAGS -DDISKAUD_SUPPORT"
AUDIO_SUBDIRS="$AUDIO_SUBDIRS disk"
AUDIO_DRIVERS="$AUDIO_DRIVERS disk/libaudio_disk.la"
fi
}
dnl See if we can use x86 assembly blitters
CheckNASM()
{
......@@ -1085,6 +1100,7 @@ case "$target" in
*-*-linux*)
ARCH=linux
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckALSA
......@@ -1151,6 +1167,7 @@ case "$target" in
*-*-bsdi*)
ARCH=bsdi
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckARTSC
......@@ -1194,6 +1211,7 @@ case "$target" in
*-*-freebsd*)
ARCH=freebsd
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckARTSC
......@@ -1246,6 +1264,7 @@ case "$target" in
*-*-netbsd*)
ARCH=netbsd
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckARTSC
......@@ -1297,6 +1316,7 @@ case "$target" in
*-*-openbsd*)
ARCH=openbsd
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckARTSC
......@@ -1345,6 +1365,7 @@ case "$target" in
*-*-sysv5*)
ARCH=sysv5
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckARTSC
......@@ -1392,6 +1413,7 @@ case "$target" in
ARCH=solaris
CFLAGS="$CFLAGS -D__ELF__" # Fix for nasm on Solaris x86
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckOSS
CheckARTSC
......@@ -1438,6 +1460,7 @@ case "$target" in
*-*-irix*)
ARCH=irix
CheckDummyVideo
CheckDiskAudio
CheckNAS
CheckX11
CheckAAlib
......@@ -1496,6 +1519,7 @@ case "$target" in
*-*-hpux*)
ARCH=hpux
CheckDummyVideo
CheckDiskAudio
CheckOSS
CheckNAS
CheckX11
......@@ -1540,6 +1564,7 @@ case "$target" in
*-*-aix*)
ARCH=aix
CheckDummyVideo
CheckDiskAudio
CheckOSS
CheckNAS
CheckX11
......@@ -1583,6 +1608,7 @@ case "$target" in
*-*-osf*)
ARCH=osf
CheckDummyVideo
CheckDiskAudio
CheckNAS
CheckX11
CheckGGI
......@@ -1626,6 +1652,7 @@ case "$target" in
*-*-qnx*)
ARCH=qnx
CheckDummyVideo
CheckDiskAudio
CheckNAS
CheckPHOTON
CheckX11
......@@ -1680,6 +1707,7 @@ case "$target" in
fi
fi
CheckDummyVideo
CheckDiskAudio
CheckWIN32
CheckDIRECTX
CheckNASM
......@@ -1736,6 +1764,7 @@ case "$target" in
ARCH=beos
ac_default_prefix=/boot/develop/tools/gnupro
CheckDummyVideo
CheckDiskAudio
CheckNASM
CheckBWINDOW
CheckBeGL
......@@ -1781,6 +1810,7 @@ case "$target" in
# for which this case would be handy.
ARCH=macos
CheckDummyVideo
CheckDiskAudio
CheckTOOLBOX
CheckMacGL
# Set up files for the main() stub
......@@ -1824,6 +1854,7 @@ case "$target" in
# config.guess comes back with "darwin", so go with the flow.
ARCH=macos
CheckDummyVideo
CheckDiskAudio
CheckCARBON
CheckMacGL
CheckPTHREAD
......@@ -1973,6 +2004,7 @@ src/audio/sun/Makefile
src/audio/ums/Makefile
src/audio/windib/Makefile
src/audio/windx5/Makefile
src/audio/disk/Makefile
src/video/Makefile
src/video/cybergfx/Makefile
src/video/x11/Makefile
......
......@@ -16,6 +16,7 @@ be found at the <A HREF="http://www.libsdl.org/"> main SDL page</A>.
Major changes since SDL 1.0.0:
</H2>
<UL>
<LI> 1.2.1: Added an audio driver that writes to disk (thanks Ryan!)
<LI> 1.2.1: Mouse wheel sends mouse button (4/5) events on Windows
<LI> 1.2.1: Added MacOS X Project Builder projects (thanks Darrell!)
<LI> 1.2.1: Added initial support for Quartz video (thanks Darrell!)
......
......@@ -5,8 +5,7 @@ noinst_LTLIBRARIES = libaudio.la
# Define which subdirectories need to be built
SUBDIRS = @AUDIO_SUBDIRS@
DIST_SUBDIRS = alsa arts baudio dma dmedia dsp esd macrom nas nto \
openbsd paudio sun ums windib windx5
DIST_SUBDIRS = alsa arts baudio dma dmedia dsp esd macrom nas nto openbsd paudio sun ums windib windx5 disk
DRIVERS = @AUDIO_DRIVERS@
......
......@@ -81,7 +81,9 @@ static AudioBootStrap *bootstrap[] = {
#ifdef ENABLE_AHI
&AHI_bootstrap,
#endif
#ifdef DISKAUD_SUPPORT
&DISKAUD_bootstrap,
#endif
NULL
};
SDL_AudioDevice *current_audio = NULL;
......
......@@ -140,6 +140,9 @@ extern AudioBootStrap SNDMGR_bootstrap;
#ifdef ENABLE_AHI
extern AudioBootStrap AHI_bootstrap;
#endif
#ifdef DISKAUD_SUPPORT
extern AudioBootStrap DISKAUD_bootstrap;
#endif
/* This is the current audio device */
extern SDL_AudioDevice *current_audio;
......
Makefile.in
Makefile
.libs
*.o
*.lo
*.la
## Makefile.am for SDL audio "driver" that writes to a file.
noinst_LTLIBRARIES = libaudio_disk.la
libaudio_disk_la_SOURCES = $(SRCS)
# The SDL audio driver sources
SRCS = SDL_diskaudio.c \
SDL_diskaudio.h
/*
SDL - Simple DirectMedia Layer
Copyright (C) 1997, 1998, 1999, 2000, 2001 Sam Lantinga
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Sam Lantinga
slouken@devolution.com
This file hacked^H^H^H^H^H^Hwritten by Ryan C. Gordon
(icculus@linuxgames.com)
*/
#ifdef SAVE_RCSID
static char rcsid =
"@(#) $Id$";
#endif
/* Output raw audio data to a file. */
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <errno.h>
#include <unistd.h>
#include <sys/stat.h>
#include <sys/types.h>
#include <sys/stat.h>
#include <fcntl.h>
#include "SDL_audio.h"
#include "SDL_error.h"
#include "SDL_audiomem.h"
#include "SDL_audio_c.h"
#include "SDL_timer.h"
#include "SDL_audiodev_c.h"
#include "SDL_diskaudio.h"
/* The tag name used by DISK audio */
#define DISKAUD_DRIVER_NAME "disk"
/* environment variables and defaults. */
#define DISKENVR_OUTFILE "SDL_DISKAUDIOFILE"
#define DISKDEFAULT_OUTFILE "sdlaudio.raw"
#define DISKENVR_WRITEDELAY "SDL_DISKAUDIODELAY"
#define DISKDEFAULT_WRITEDELAY 150
/* Audio driver functions */
static int DISKAUD_OpenAudio(_THIS, SDL_AudioSpec *spec);
static void DISKAUD_WaitAudio(_THIS);
static void DISKAUD_PlayAudio(_THIS);
static Uint8 *DISKAUD_GetAudioBuf(_THIS);
static void DISKAUD_CloseAudio(_THIS);
static const char *DISKAUD_GetOutputFilename(void)
{
const char *envr = getenv(DISKENVR_OUTFILE);
return((envr != NULL) ? envr : DISKDEFAULT_OUTFILE);
}
/* Audio driver bootstrap functions */
static int DISKAUD_Available(void)
{
#if 0
int fd;
int available;
int exists = 0;
struct stat statbuf;
const char *fname = DISKAUD_GetOutputFilename();
available = 0;
if (stat(fname, &statbuf) == 0)
exists = 1;
fd = open(fname, O_WRONLY | O_CREAT | O_APPEND, S_IRUSR | S_IWUSR);
if ( fd != -1 ) {
available = 1;
close(fd);
if (!exists) {
unlink(fname);
}
}
return(available);
#else
return(1);
#endif
}
static void DISKAUD_DeleteDevice(SDL_AudioDevice *device)
{
free(device->hidden);
free(device);
}
static SDL_AudioDevice *DISKAUD_CreateDevice(int devindex)
{
SDL_AudioDevice *this;
const char *envr;
/* Initialize all variables that we clean on shutdown */
this = (SDL_AudioDevice *)malloc(sizeof(SDL_AudioDevice));
if ( this ) {
memset(this, 0, (sizeof *this));
this->hidden = (struct SDL_PrivateAudioData *)
malloc((sizeof *this->hidden));
}
if ( (this == NULL) || (this->hidden == NULL) ) {
SDL_OutOfMemory();
if ( this ) {
free(this);
}
return(0);
}
memset(this->hidden, 0, (sizeof *this->hidden));
envr = getenv(DISKENVR_WRITEDELAY);
this->hidden->write_delay = (envr) ? atoi(envr) : DISKDEFAULT_WRITEDELAY;
/* Set the function pointers */
this->OpenAudio = DISKAUD_OpenAudio;
this->WaitAudio = DISKAUD_WaitAudio;
this->PlayAudio = DISKAUD_PlayAudio;
this->GetAudioBuf = DISKAUD_GetAudioBuf;
this->CloseAudio = DISKAUD_CloseAudio;
this->free = DISKAUD_DeleteDevice;
return this;
}
AudioBootStrap DISKAUD_bootstrap = {
DISKAUD_DRIVER_NAME, "direct-to-disk audio",
DISKAUD_Available, DISKAUD_CreateDevice
};
/* This function waits until it is possible to write a full sound buffer */
static void DISKAUD_WaitAudio(_THIS)
{
SDL_Delay(this->hidden->write_delay);
}
static void DISKAUD_PlayAudio(_THIS)
{
int written;
/* Write the audio data, checking for EAGAIN on broken audio drivers */
do {
written = write(this->hidden->audio_fd,
this->hidden->mixbuf,
this->hidden->mixlen);
if ( (written < 0) && ((errno == 0) || (errno == EAGAIN)) ) {
SDL_Delay(1); /* Let a little CPU time go by */
}
} while ( (written < 0) &&
((errno == 0) || (errno == EAGAIN) || (errno == EINTR)) );
/* 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 *DISKAUD_GetAudioBuf(_THIS)
{
return(this->hidden->mixbuf);
}
static void DISKAUD_CloseAudio(_THIS)
{
if ( this->hidden->mixbuf != NULL ) {
SDL_FreeAudioMem(this->hidden->mixbuf);
this->hidden->mixbuf = NULL;
}
if ( this->hidden->audio_fd >= 0 ) {
close(this->hidden->audio_fd);
this->hidden->audio_fd = -1;
}
}
static int DISKAUD_OpenAudio(_THIS, SDL_AudioSpec *spec)
{
const char *fname = DISKAUD_GetOutputFilename();
/* Open the audio device */
this->hidden->audio_fd = open(fname, O_WRONLY | O_CREAT, S_IRUSR | S_IWUSR);
if ( this->hidden->audio_fd < 0 ) {
SDL_SetError("Couldn't open %s: %s", fname, strerror(errno));
return(-1);
}
fprintf(stderr, "WARNING: You are using the SDL disk writer"
" audio driver!\n Writing to file [%s].\n", fname);
/* Allocate mixing buffer */
this->hidden->mixlen = spec->size;
this->hidden->mixbuf = (Uint8 *) SDL_AllocAudioMem(this->hidden->mixlen);
if ( this->hidden->mixbuf == NULL ) {
return(-1);
}
memset(this->hidden->mixbuf, spec->silence, spec->size);
/* We're ready to rock and roll. :-) */
return(0);
}
/*
SDL - Simple DirectMedia Layer
Copyright (C) 1997, 1998, 1999, 2000, 2001 Sam Lantinga
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
License as published by the Free Software Foundation; either
version 2 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
Library General Public License for more details.
You should have received a copy of the GNU Library General Public
License along with this library; if not, write to the Free
Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
Sam Lantinga
slouken@devolution.com
*/
#ifdef SAVE_RCSID
static char rcsid =
"@(#) $Id$";
#endif
#ifndef _SDL_diskaudio_h
#define _SDL_diskaudio_h
#include "SDL_sysaudio.h"
/* Hidden "this" pointer for the video functions */
#define _THIS SDL_AudioDevice *this
struct SDL_PrivateAudioData {
/* The file descriptor for the audio device */
int audio_fd;
Uint8 *mixbuf;
Uint32 mixlen;
Uint32 write_delay;
};
#endif /* _SDL_diskaudio_h */
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment