openbsd-ports/comms/gmfsk/patches/patch-src_snd_c
jakemsr e195e84870 sndio supported as default audio output method
testing hints from sthen@, thanks
2010-04-26 01:47:15 +00:00

353 lines
8.4 KiB
Plaintext

$OpenBSD: patch-src_snd_c,v 1.2 2010/04/26 01:47:15 jakemsr Exp $
--- src/snd.c.orig Sat Apr 17 10:24:11 2004
+++ src/snd.c Sun Apr 18 16:52:21 2010
@@ -36,8 +36,7 @@
#include <fcntl.h>
#include <time.h>
-#include <sys/soundcard.h>
-#include <sys/ioctl.h>
+#include <sndio.h>
#include "snd.h"
#include "misc.h"
@@ -55,6 +54,7 @@
static snd_config_t config;
static snd_config_t newconfig;
+static struct sio_hdl *hdl = NULL;
static gint snd_fd = -1;
static gint snd_dir = 0;
@@ -133,18 +133,17 @@ static void dprintf(const char *fmt, ...)
/* ---------------------------------------------------------------------- */
-static gint opensnd(gint direction)
+static struct sio_hdl * opensnd(gint direction)
{
#ifdef SND_DEBUG
- audio_buf_info info;
gchar *str;
#endif
- guint sndparam, wanted;
- gint fd;
+ struct sio_hdl *h;
+ struct sio_par par, gpar;
if (!config.device) {
snderr("opensnd: device not set");
- return -1;
+ return NULL;
}
#ifdef SND_DEBUG
@@ -165,18 +164,16 @@ static gint opensnd(gint direction)
dprintf("Opening %s for %s...\n", config.device, str);
#endif
- /* non-blocking open */
- if ((fd = open(config.device, direction | O_NONBLOCK)) < 0) {
- snderr("opensnd: open: %s: %m", config.device);
- return -1;
+ if (!strncmp(config.device, "", 1) ||
+ !strncmp(config.device, "default", 8))
+ h = sio_open(NULL, direction, 0);
+ else
+ h = sio_open(config.device, direction, 0);
+ if (!h) {
+ snderr("opensnd: open: %s", config.device);
+ return NULL;
}
- /* make it block again - (SNDCTL_DSP_NONBLOCK ???) */
- if (fcntl(fd, F_SETFL, fcntl(fd, F_GETFL) & ~O_NONBLOCK) < 0) {
- snderr("opensnd: ioctl: SNDCTL_DSP_NONBLOCK: %m");
- goto error;
- }
-
#ifdef SND_DEBUG
if (config.flags & SND_FLAG_8BIT)
str = "8 bit unsigned";
@@ -186,20 +183,15 @@ static gint opensnd(gint direction)
dprintf("Setting sample format (%s)...\n", str);
#endif
- if (config.flags & SND_FLAG_8BIT)
- wanted = AFMT_U8; /* 8 bit unsigned */
- else
- wanted = AFMT_S16_NE; /* 16 bit signed, native byteorder */
+ sio_initpar(&par);
- sndparam = wanted;
- if (ioctl(fd, SNDCTL_DSP_SETFMT, &sndparam) < 0) {
- snderr("opensnd: ioctl: SNDCTL_DSP_SETFMT: %m");
- goto error;
+ if (config.flags & SND_FLAG_8BIT) {
+ par.bits = 8;
+ par.sig = 0;
+ } else {
+ par.bits = 16;
+ par.sig = 1;
}
- if (sndparam != wanted) {
- snderr("opensnd: Requested sample format not supported");
- goto error;
- }
#ifdef SND_DEBUG
dprintf("Setting %s audio...\n",
@@ -207,85 +199,50 @@ static gint opensnd(gint direction)
#endif
if (config.flags & SND_FLAG_STEREO)
- wanted = 1; /* stereo */
+ par.pchan = par.rchan = 2;
else
- wanted = 0; /* mono */
+ par.pchan = par.rchan = 1;
- sndparam = wanted;
- if (ioctl(fd, SNDCTL_DSP_STEREO, &sndparam) < 0) {
- snderr("opensnd: ioctl: SNDCTL_DSP_STEREO: %m");
- goto error;
- }
- if (sndparam != wanted) {
- snderr("opensnd: Cannot set %s audio",
- (config.flags & SND_FLAG_STEREO) ? "stereo" : "mono");
- goto error;
- }
-
#ifdef SND_DEBUG
dprintf("Setting samplerate to %u...\n", config.samplerate);
#endif
- sndparam = config.samplerate;
- if (ioctl(fd, SNDCTL_DSP_SPEED, &sndparam) < 0) {
- snderr("opensnd: ioctl: SNDCTL_DSP_SPEED: %m");
- goto error;
- }
- if (sndparam != config.samplerate) {
- g_warning("Sampling rate is %u, requested %u\n",
- sndparam,
- config.samplerate);
- }
- config.samplerate = sndparam;
+ par.rate = config.samplerate;
/* Request a buffer size of 512 samples */
- if (config.flags & SND_FLAG_8BIT)
- sndparam = 0x00000009;
- else
- sndparam = 0x0000000A;
+ par.round = 512;
+ par.appbufsz = par.round * 4;
- if (config.flags & SND_FLAG_STEREO)
- sndparam += 1;
-
- /* Unlimited amount of buffers for RX, four for TX */
- if (direction == O_RDONLY)
- sndparam |= 0x7FFF0000;
- else
- sndparam |= 0x00040000;
-
#ifdef SND_DEBUG
- dprintf("Setting fragment size (param = 0x%08X)...\n", sndparam);
+ dprintf("-- \n");
#endif
- if (ioctl(fd, SNDCTL_DSP_SETFRAGMENT, &sndparam) < 0) {
- snderr("opensnd: ioctl: SNDCTL_DSP_SETFRAGMENT: %m");
+ if (!sio_setpar(h, &par) || !sio_getpar(h, &gpar) ||
+ gpar.bits != par.bits || gpar.sig != par.sig) {
+ snderr("sndopen: could not set parameters as desired");
goto error;
}
#ifdef SND_DEBUG
- if (direction == O_RDONLY) {
- if (ioctl(fd, SNDCTL_DSP_GETISPACE, &info) < 0) {
- dprintf("ioctl: SNDCTL_DSP_GETISPACE: %m");
- }
- } else {
- if (ioctl(fd, SNDCTL_DSP_GETOSPACE, &info) < 0) {
- dprintf("ioctl: SNDCTL_DSP_GETOSPACE: %m");
- }
- }
-
- dprintf("Audio buffer size: %d bytes, number of buffers: %d\n",
- info.fragsize, info.fragstotal);
+ dprintf("samplerate: %u / want %u\n",
+ gpar.rate, config.samplerate);
+ dprintf("channels: play %u / record %u / want %u\n",
+ gpar.pchan, gpar.rchan,
+ (config.flags & SND_FLAG_STEREO) ? 2 : 1);
#endif
-#ifdef SND_DEBUG
- dprintf("-- \n");
-#endif
+ config.samplerate = gpar.rate;
- return fd;
+ if (!sio_start(h)) {
+ snderr("sndopen: could not start sndio");
+ goto error;
+ }
+ return h;
+
error:
- close(fd);
- return -1;
+ sio_close(h);
+ return NULL;
}
/* ---------------------------------------------------------------------- */
@@ -307,11 +264,9 @@ gint sound_open_for_write(gint rate)
if (config.flags & SND_FLAG_TESTMODE_MASK)
snd_fd = 1;
else if (!(config.flags & SND_FLAG_FULLDUP))
- snd_fd = opensnd(O_WRONLY);
- else if (snd_fd < 0)
- snd_fd = opensnd(O_RDWR);
+ hdl = opensnd(SIO_PLAY);
- if (snd_fd < 0)
+ if (hdl == NULL && snd_fd != 1)
return -1;
snd_dir = O_WRONLY;
@@ -323,14 +278,14 @@ gint sound_open_for_write(gint rate)
src_delete(tx_src_state);
tx_src_state = NULL;
}
- return snd_fd;
+ return 0;
}
ratio = real_rate / rate;
if (tx_src_state && tx_src_data && tx_src_data->src_ratio == ratio) {
src_reset(tx_src_state);
- return snd_fd;
+ return 0;
}
#if SND_DEBUG
@@ -354,7 +309,7 @@ gint sound_open_for_write(gint rate)
tx_src_data->src_ratio = ratio;
- return snd_fd;
+ return 0;
}
gint sound_open_for_read(gint rate)
@@ -374,11 +329,9 @@ gint sound_open_for_read(gint rate)
if (config.flags & SND_FLAG_TESTMODE_MASK)
snd_fd = 0;
else if (!(config.flags & SND_FLAG_FULLDUP))
- snd_fd = opensnd(O_RDONLY);
- else if (snd_fd < 0)
- snd_fd = opensnd(O_RDWR);
+ hdl = opensnd(SIO_REC);
- if (snd_fd < 0)
+ if (hdl == NULL && snd_fd != 0)
return -1;
snd_dir = O_RDONLY;
@@ -390,14 +343,14 @@ gint sound_open_for_read(gint rate)
src_delete(rx_src_state);
rx_src_state = NULL;
}
- return snd_fd;
+ return 0;
}
ratio = rate / real_rate;
if (rx_src_state && rx_src_data && rx_src_data->src_ratio == ratio) {
src_reset(rx_src_state);
- return snd_fd;
+ return 0;
}
#if SND_DEBUG
@@ -421,7 +374,7 @@ gint sound_open_for_read(gint rate)
rx_src_data->src_ratio = ratio;
- return snd_fd;
+ return 0;
}
void sound_close(void)
@@ -451,13 +404,7 @@ void sound_close(void)
}
#endif
- /* never close stdin/out/err */
- if (snd_fd > 2) {
- if (ioctl(snd_fd, SNDCTL_DSP_SYNC, 0) < 0)
- snderr("sound_close: ioctl: SNDCTL_DSP_SYNC: %m");
- close(snd_fd);
- snd_fd = -1;
- }
+ sio_close(hdl);
}
char *sound_error(void)
@@ -477,8 +424,8 @@ gint sound_write(gfloat *buf, gint cnt)
if ((config.flags & SND_FLAG_TESTMODE_MASK) == SND_FLAG_TESTMODE_RX)
return cnt;
- if (snd_fd < 0) {
- snderr("sound_write: fd < 0");
+ if (hdl == NULL) {
+ snderr("sound_write: hdl == NULL");
return -1;
}
@@ -539,7 +486,7 @@ static gint write_samples(gfloat *buf, gint count)
if (config.flags & SND_FLAG_STEREO)
count *= 2;
- if ((i = write(snd_fd, p, count)) < 0)
+ if ((i = sio_write(hdl, p, count)) < 0)
snderr("write_samples: write: %m");
return i;
@@ -573,8 +520,8 @@ gint sound_read(gfloat **buffer, gint *count)
return 0;
}
- if (snd_fd < 0) {
- snderr("sound_read: fd < 0");
+ if (hdl == NULL) {
+ snderr("sound_read: hdl == NULL");
return -1;
}
@@ -625,7 +572,7 @@ static gint read_samples(gfloat *buf, gint count)
if (config.flags & SND_FLAG_8BIT) {
count *= sizeof(guint8);
- if ((len = read(snd_fd, snd_b_buffer, count)) < 0)
+ if ((len = sio_read(hdl, snd_b_buffer, count)) < 0)
goto error;
len /= sizeof(guint8);
@@ -641,7 +588,7 @@ static gint read_samples(gfloat *buf, gint count)
} else {
count *= sizeof(gint16);
- if ((len = read(snd_fd, snd_w_buffer, count)) < 0)
+ if ((len = sio_read(hdl, snd_w_buffer, count)) < 0)
goto error;
len /= sizeof(gint16);