aboutsummaryrefslogtreecommitdiff
path: root/plugins/dfsound
diff options
context:
space:
mode:
Diffstat (limited to 'plugins/dfsound')
-rw-r--r--plugins/dfsound/alsa.c50
-rw-r--r--plugins/dfsound/dsoundoss.h21
-rw-r--r--plugins/dfsound/nullsnd.c24
-rw-r--r--plugins/dfsound/oss.c54
-rw-r--r--plugins/dfsound/out.c51
-rw-r--r--plugins/dfsound/out.h12
-rw-r--r--plugins/dfsound/pulseaudio.c38
-rw-r--r--plugins/dfsound/sdl.c29
-rw-r--r--plugins/dfsound/spu.c8
-rw-r--r--plugins/dfsound/stdafx.h3
10 files changed, 186 insertions, 104 deletions
diff --git a/plugins/dfsound/alsa.c b/plugins/dfsound/alsa.c
index c67943a..58900cc 100644
--- a/plugins/dfsound/alsa.c
+++ b/plugins/dfsound/alsa.c
@@ -15,21 +15,17 @@
* *
***************************************************************************/
-#include "stdafx.h"
-
-#define _IN_OSS
-
-#include "externals.h"
-
+#include <stdio.h>
#define ALSA_PCM_NEW_HW_PARAMS_API
#define ALSA_PCM_NEW_SW_PARAMS_API
#include <alsa/asoundlib.h>
+#include "out.h"
static snd_pcm_t *handle = NULL;
static snd_pcm_uframes_t buffer_size;
// SETUP SOUND
-void SetupSound(void)
+static int alsa_init(void)
{
snd_pcm_hw_params_t *hwparams;
snd_pcm_status_t *status;
@@ -49,13 +45,13 @@ void SetupSound(void)
SND_PCM_STREAM_PLAYBACK, SND_PCM_NONBLOCK)) < 0)
{
printf("Audio open error: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err = snd_pcm_nonblock(handle, 0))<0)
{
printf("Can't set blocking moded: %s\n", snd_strerror(err));
- return;
+ return -1;
}
snd_pcm_hw_params_alloca(&hwparams);
@@ -63,63 +59,64 @@ void SetupSound(void)
if((err=snd_pcm_hw_params_any(handle, hwparams))<0)
{
printf("Broken configuration for this PCM: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params_set_access(handle, hwparams, SND_PCM_ACCESS_RW_INTERLEAVED))<0)
{
printf("Access type not available: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params_set_format(handle, hwparams, format))<0)
{
printf("Sample format not available: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params_set_channels(handle, hwparams, pchannels))<0)
{
printf("Channels count not available: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params_set_rate_near(handle, hwparams, &pspeed, 0))<0)
{
printf("Rate not available: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params_set_buffer_time_near(handle, hwparams, &buffer_time, 0))<0)
{
printf("Buffer time error: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params_set_period_time_near(handle, hwparams, &period_time, 0))<0)
{
printf("Period time error: %s\n", snd_strerror(err));
- return;
+ return -1;
}
if((err=snd_pcm_hw_params(handle, hwparams))<0)
{
printf("Unable to install hw params: %s\n", snd_strerror(err));
- return;
+ return -1;
}
snd_pcm_status_alloca(&status);
if((err=snd_pcm_status(handle, status))<0)
{
printf("Unable to get status: %s\n", snd_strerror(err));
- return;
+ return -1;
}
buffer_size = snd_pcm_status_get_avail(status);
+ return 0;
}
// REMOVE SOUND
-void RemoveSound(void)
+static void alsa_finish(void)
{
if(handle != NULL)
{
@@ -130,9 +127,9 @@ void RemoveSound(void)
}
// GET BYTES BUFFERED
-unsigned long SoundGetBytesBuffered(void)
+static int alsa_busy(void)
{
- unsigned long l;
+ int l;
if (handle == NULL) // failed to open?
return 1;
@@ -146,7 +143,7 @@ unsigned long SoundGetBytesBuffered(void)
}
// FEED SOUND DATA
-void SoundFeedStreamData(unsigned char* pSound,long lBytes)
+static void alsa_feed(void *pSound, int lBytes)
{
if (handle == NULL) return;
@@ -154,3 +151,12 @@ void SoundFeedStreamData(unsigned char* pSound,long lBytes)
snd_pcm_prepare(handle);
snd_pcm_writei(handle,pSound, lBytes / 4);
}
+
+void out_register_alsa(struct out_driver *drv)
+{
+ drv->name = "alsa";
+ drv->init = alsa_init;
+ drv->finish = alsa_finish;
+ drv->busy = alsa_busy;
+ drv->feed = alsa_feed;
+}
diff --git a/plugins/dfsound/dsoundoss.h b/plugins/dfsound/dsoundoss.h
deleted file mode 100644
index 543b297..0000000
--- a/plugins/dfsound/dsoundoss.h
+++ /dev/null
@@ -1,21 +0,0 @@
-/***************************************************************************
- dsoundoss.h - description
- -------------------
- begin : Wed May 15 2002
- copyright : (C) 2002 by Pete Bernert
- email : BlackDove@addcom.de
- ***************************************************************************/
-/***************************************************************************
- * *
- * This program is free software; you can redistribute it and/or modify *
- * it under the terms of the GNU General Public License as published by *
- * the Free Software Foundation; either version 2 of the License, or *
- * (at your option) any later version. See also the license.txt file for *
- * additional informations. *
- * *
- ***************************************************************************/
-
-void SetupSound(void);
-void RemoveSound(void);
-unsigned long SoundGetBytesBuffered(void);
-void SoundFeedStreamData(unsigned char* pSound,long lBytes);
diff --git a/plugins/dfsound/nullsnd.c b/plugins/dfsound/nullsnd.c
index bf07909..d8714df 100644
--- a/plugins/dfsound/nullsnd.c
+++ b/plugins/dfsound/nullsnd.c
@@ -1,24 +1,32 @@
-#include "stdafx.h"
-#define _IN_OSS
-#include "externals.h"
+#include "out.h"
// SETUP SOUND
-void SetupSound(void)
+static int none_init(void)
{
+ return 0;
}
// REMOVE SOUND
-void RemoveSound(void)
+static void none_finish(void)
{
}
// GET BYTES BUFFERED
-unsigned long SoundGetBytesBuffered(void)
+static int none_busy(void)
{
- return 0;
+ return 1;
}
// FEED SOUND DATA
-void SoundFeedStreamData(unsigned char* pSound,long lBytes)
+static void none_feed(void *buf, int bytes)
+{
+}
+
+void out_register_none(struct out_driver *drv)
{
+ drv->name = "none";
+ drv->init = none_init;
+ drv->finish = none_finish;
+ drv->busy = none_busy;
+ drv->feed = none_feed;
}
diff --git a/plugins/dfsound/oss.c b/plugins/dfsound/oss.c
index 04d7446..709cb37 100644
--- a/plugins/dfsound/oss.c
+++ b/plugins/dfsound/oss.c
@@ -15,11 +15,14 @@
* *
***************************************************************************/
-#include "stdafx.h"
-
-#define _IN_OSS
-
-#include "externals.h"
+#include <stdio.h>
+#include <sys/types.h>
+#include <sys/stat.h>
+#include <fcntl.h>
+#include <sys/ioctl.h>
+#include <unistd.h>
+#include <sys/soundcard.h>
+#include "out.h"
////////////////////////////////////////////////////////////////////////
// oss globals
@@ -37,7 +40,7 @@ extern int errno;
// SETUP SOUND
////////////////////////////////////////////////////////////////////////
-void SetupSound(void)
+static int oss_init(void)
{
int pspeed=44100;
int pstereo;
@@ -52,14 +55,14 @@ void SetupSound(void)
if((oss_audio_fd=open("/dev/dsp",O_WRONLY,0))==-1)
{
- printf("Sound device not available!\n");
- return;
+ printf("OSS device not available\n");
+ return -1;
}
if(ioctl(oss_audio_fd,SNDCTL_DSP_RESET,0)==-1)
{
printf("Sound reset failed\n");
- return;
+ return -1;
}
// we use 64 fragments with 1024 bytes each
@@ -71,7 +74,7 @@ void SetupSound(void)
if(ioctl(oss_audio_fd,SNDCTL_DSP_SETFRAGMENT,&myfrag)==-1)
{
printf("Sound set fragment failed!\n");
- return;
+ return -1;
}
format = AFMT_S16_NE;
@@ -79,39 +82,41 @@ void SetupSound(void)
if(ioctl(oss_audio_fd,SNDCTL_DSP_SETFMT,&format) == -1)
{
printf("Sound format not supported!\n");
- return;
+ return -1;
}
if(format!=AFMT_S16_NE)
{
printf("Sound format not supported!\n");
- return;
+ return -1;
}
if(ioctl(oss_audio_fd,SNDCTL_DSP_STEREO,&oss_stereo)==-1 || !oss_stereo)
{
printf("Stereo mode not supported!\n");
- return;
+ return -1;
}
if(ioctl(oss_audio_fd,SNDCTL_DSP_SPEED,&oss_speed)==-1)
{
printf("Sound frequency not supported\n");
- return;
+ return -1;
}
if(oss_speed!=pspeed)
{
printf("Sound frequency not supported\n");
- return;
+ return -1;
}
+
+ return 0;
}
////////////////////////////////////////////////////////////////////////
// REMOVE SOUND
////////////////////////////////////////////////////////////////////////
-void RemoveSound(void)
+static void oss_finish(void)
{
if(oss_audio_fd != -1 )
{
@@ -121,10 +126,10 @@ void RemoveSound(void)
}
////////////////////////////////////////////////////////////////////////
-// GET BYTES BUFFERED
+// GET BUFFERED STATUS
////////////////////////////////////////////////////////////////////////
-unsigned long SoundGetBytesBuffered(void)
+static int oss_busy(void)
{
audio_buf_info info;
unsigned long l;
@@ -146,8 +151,17 @@ unsigned long SoundGetBytesBuffered(void)
// FEED SOUND DATA
////////////////////////////////////////////////////////////////////////
-void SoundFeedStreamData(unsigned char* pSound,long lBytes)
+static void oss_feed(void *buf, int bytes)
{
if(oss_audio_fd == -1) return;
- write(oss_audio_fd,pSound,lBytes);
+ write(oss_audio_fd, buf, bytes);
+}
+
+void out_register_oss(struct out_driver *drv)
+{
+ drv->name = "oss";
+ drv->init = oss_init;
+ drv->finish = oss_finish;
+ drv->busy = oss_busy;
+ drv->feed = oss_feed;
}
diff --git a/plugins/dfsound/out.c b/plugins/dfsound/out.c
new file mode 100644
index 0000000..150d718
--- /dev/null
+++ b/plugins/dfsound/out.c
@@ -0,0 +1,51 @@
+#include <stdio.h>
+#include <stdlib.h>
+#include "out.h"
+
+#define MAX_OUT_DRIVERS 5
+
+static struct out_driver out_drivers[MAX_OUT_DRIVERS];
+struct out_driver *out_current;
+static int driver_count;
+
+#define REGISTER_DRIVER(d) { \
+ extern void out_register_##d(struct out_driver *drv); \
+ out_register_##d(&out_drivers[driver_count++]); \
+}
+
+void SetupSound(void)
+{
+ int i;
+
+ if (driver_count == 0) {
+#ifdef HAVE_OSS
+ REGISTER_DRIVER(oss);
+#endif
+#ifdef HAVE_ALSA
+ REGISTER_DRIVER(alsa);
+#endif
+#ifdef HAVE_SDL
+ REGISTER_DRIVER(sdl);
+#endif
+#ifdef HAVE_PULSE
+ REGISTER_DRIVER(pulse);
+#endif
+#ifdef HAVE_LIBRETRO
+ REGISTER_DRIVER(libretro);
+#endif
+ REGISTER_DRIVER(none);
+ }
+
+ for (i = 0; i < driver_count; i++)
+ if (out_drivers[i].init() == 0)
+ break;
+
+ if (i < 0 || i >= driver_count) {
+ printf("the impossible happened\n");
+ abort();
+ }
+
+ out_current = &out_drivers[i];
+ printf("selected sound output driver: %s\n", out_current->name);
+}
+
diff --git a/plugins/dfsound/out.h b/plugins/dfsound/out.h
new file mode 100644
index 0000000..4607099
--- /dev/null
+++ b/plugins/dfsound/out.h
@@ -0,0 +1,12 @@
+
+struct out_driver {
+ const char *name;
+ int (*init)(void);
+ void (*finish)(void);
+ int (*busy)(void);
+ void (*feed)(void *data, int bytes);
+};
+
+extern struct out_driver *out_current;
+
+void SetupSound(void);
diff --git a/plugins/dfsound/pulseaudio.c b/plugins/dfsound/pulseaudio.c
index 1dadd88..057c2c4 100644
--- a/plugins/dfsound/pulseaudio.c
+++ b/plugins/dfsound/pulseaudio.c
@@ -19,8 +19,6 @@ comment : Much of this was taken from simple.c, in the pulseaudio
#include "stdafx.h"
-#ifdef USEPULSEAUDIO
-
#define _IN_OSS
#include "externals.h"
@@ -136,7 +134,7 @@ static void stream_request_cb (pa_stream *stream, size_t length, void *userdata)
// SETUP SOUND
////////////////////////////////////////////////////////////////////////
-void SetupSound (void)
+static void pulse_init(void)
{
int error_number;
@@ -145,7 +143,7 @@ void SetupSound (void)
if (device.mainloop == NULL)
{
fprintf (stderr, "Could not acquire PulseAudio main loop\n");
- return;
+ return -1;
}
// Acquire context ////////////////////////////////////////////////////////
@@ -156,7 +154,7 @@ void SetupSound (void)
if (device.context == NULL)
{
fprintf (stderr, "Could not acquire PulseAudio device context\n");
- return;
+ return -1;
}
// Connect to PulseAudio server ///////////////////////////////////////////
@@ -164,7 +162,7 @@ void SetupSound (void)
{
error_number = pa_context_errno (device.context);
fprintf (stderr, "Could not connect to PulseAudio server: %s\n", pa_strerror(error_number));
- return;
+ return -1;
}
// Run mainloop until sever context is ready //////////////////////////////
@@ -172,7 +170,7 @@ void SetupSound (void)
if (pa_threaded_mainloop_start (device.mainloop) < 0)
{
fprintf (stderr, "Could not start mainloop\n");
- return;
+ return -1;
}
pa_context_state_t context_state;
@@ -184,7 +182,7 @@ void SetupSound (void)
{
error_number = pa_context_errno (device.context);
fprintf (stderr, "Context state is not good: %s\n", pa_strerror (error_number));
- return;
+ return -1;
}
else if (context_state == PA_CONTEXT_READY)
break;
@@ -216,7 +214,7 @@ void SetupSound (void)
{
error_number = pa_context_errno (device.context);
fprintf (stderr, "Could not acquire new PulseAudio stream: %s\n", pa_strerror (error_number));
- return;
+ return -1;
}
// Set callbacks for server events ////////////////////////////////////////
@@ -231,7 +229,7 @@ void SetupSound (void)
{
pa_context_errno (device.context);
fprintf (stderr, "Could not connect for playback: %s\n", pa_strerror (error_number));
- return;
+ return -1;
}
// Run mainloop until stream is ready /////////////////////////////////////
@@ -248,7 +246,7 @@ void SetupSound (void)
{
error_number = pa_context_errno (device.context);
fprintf (stderr, "Stream state is not good: %s\n", pa_strerror (error_number));
- return;
+ return -1;
}
else
fprintf (stderr, "PulseAudio stream state is %d\n", stream_state);
@@ -258,13 +256,13 @@ void SetupSound (void)
pa_threaded_mainloop_unlock (device.mainloop);
fprintf (stderr, "PulseAudio should be connected\n");
- return;
+ return 0;
}
////////////////////////////////////////////////////////////////////////
// REMOVE SOUND
////////////////////////////////////////////////////////////////////////
-void RemoveSound (void)
+static void pulse_finish(void)
{
if (device.mainloop != NULL)
pa_threaded_mainloop_stop (device.mainloop);
@@ -295,7 +293,7 @@ void RemoveSound (void)
// GET BYTES BUFFERED
////////////////////////////////////////////////////////////////////////
-unsigned long SoundGetBytesBuffered (void)
+static int pulse_busy(void)
{
int free_space;
int error_code;
@@ -329,7 +327,7 @@ unsigned long SoundGetBytesBuffered (void)
// FEED SOUND DATA
////////////////////////////////////////////////////////////////////////
-void SoundFeedStreamData (unsigned char *pSound, long lBytes)
+static void pulse_feed(void *pSound, int lBytes)
{
int error_code;
int size;
@@ -348,4 +346,12 @@ void SoundFeedStreamData (unsigned char *pSound, long lBytes)
}
}
}
-#endif
+
+void out_register_pulse(struct out_driver *drv)
+{
+ drv->name = "pulseaudio";
+ drv->init = pulse_init;
+ drv->finish = pulse_finish;
+ drv->busy = pulse_busy;
+ drv->feed = pulse_feed;
+}
diff --git a/plugins/dfsound/sdl.c b/plugins/dfsound/sdl.c
index f7dc298..ce92b6e 100644
--- a/plugins/dfsound/sdl.c
+++ b/plugins/dfsound/sdl.c
@@ -16,10 +16,9 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1307 USA
*/
-#include "stdafx.h"
-
-#include "externals.h"
+#include <stdlib.h>
#include <SDL.h>
+#include "out.h"
#define BUFFER_SIZE 22050
@@ -61,10 +60,10 @@ static void DestroySDL() {
}
}
-void SetupSound(void) {
+static int sdl_init(void) {
SDL_AudioSpec spec;
- if (pSndBuffer != NULL) return;
+ if (pSndBuffer != NULL) return -1;
InitSDL();
@@ -76,7 +75,7 @@ void SetupSound(void) {
if (SDL_OpenAudio(&spec, NULL) < 0) {
DestroySDL();
- return;
+ return -1;
}
iBufSize = BUFFER_SIZE;
@@ -84,16 +83,17 @@ void SetupSound(void) {
pSndBuffer = (short *)malloc(iBufSize * sizeof(short));
if (pSndBuffer == NULL) {
SDL_CloseAudio();
- return;
+ return -1;
}
iReadPos = 0;
iWritePos = 0;
SDL_PauseAudio(0);
+ return 0;
}
-void RemoveSound(void) {
+static void sdl_finish(void) {
if (pSndBuffer == NULL) return;
SDL_CloseAudio();
@@ -103,7 +103,7 @@ void RemoveSound(void) {
pSndBuffer = NULL;
}
-unsigned long SoundGetBytesBuffered(void) {
+static int sdl_busy(void) {
int size;
if (pSndBuffer == NULL) return 1;
@@ -116,7 +116,7 @@ unsigned long SoundGetBytesBuffered(void) {
return 0;
}
-void SoundFeedStreamData(unsigned char *pSound, long lBytes) {
+static void sdl_feed(void *pSound, int lBytes) {
short *p = (short *)pSound;
if (pSndBuffer == NULL) return;
@@ -132,3 +132,12 @@ void SoundFeedStreamData(unsigned char *pSound, long lBytes) {
lBytes -= sizeof(short);
}
}
+
+void out_register_sdl(struct out_driver *drv)
+{
+ drv->name = "sdl";
+ drv->init = sdl_init;
+ drv->finish = sdl_finish;
+ drv->busy = sdl_busy;
+ drv->feed = sdl_feed;
+}
diff --git a/plugins/dfsound/spu.c b/plugins/dfsound/spu.c
index bbbe1e3..45a7886 100644
--- a/plugins/dfsound/spu.c
+++ b/plugins/dfsound/spu.c
@@ -24,7 +24,7 @@
#include "externals.h"
#include "registers.h"
-#include "dsoundoss.h"
+#include "out.h"
#ifdef ENABLE_NLS
#include <libintl.h>
@@ -697,7 +697,7 @@ static int do_samples(int forced_updates)
// until enuff free place is available/a new channel gets
// started
- if(!forced_updates && SoundGetBytesBuffered()) // still enuff data in sound buffer?
+ if(!forced_updates && out_current->busy()) // still enuff data in sound buffer?
{
return 0;
}
@@ -872,7 +872,7 @@ static int do_samples(int forced_updates)
// wanna have around 1/60 sec (16.666 ms) updates
if (iCycle++ > 16/FRAG_MSECS)
{
- SoundFeedStreamData((unsigned char *)pSpuBuffer,
+ out_current->feed(pSpuBuffer,
((unsigned char *)pS) - ((unsigned char *)pSpuBuffer));
pS = (short *)pSpuBuffer;
iCycle = 0;
@@ -1056,7 +1056,7 @@ long CALLBACK SPUclose(void)
bSPUIsOpen = 0; // no more open
- RemoveSound(); // no more sound handling
+ out_current->finish(); // no more sound handling
return 0;
}
diff --git a/plugins/dfsound/stdafx.h b/plugins/dfsound/stdafx.h
index 45b366b..d40344f 100644
--- a/plugins/dfsound/stdafx.h
+++ b/plugins/dfsound/stdafx.h
@@ -23,9 +23,6 @@
#include <sys/ioctl.h>
#include <unistd.h>
#include <fcntl.h>
-#ifdef USEOSS
-#include <sys/soundcard.h>
-#endif
#include <unistd.h>
#include <pthread.h>
#define RRand(range) (random()%range)