aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorMax Kellermann <max@duempel.org>2008-10-14 17:21:49 +0200
committerMax Kellermann <max@duempel.org>2008-10-14 17:21:49 +0200
commit86782faa18b32941eb2e39dd552d58b934279f1a (patch)
treed9f431360e66f686c8cb4f203166e9467a7a9af9
parent79a1811c1121e96918db4133872e0d05dcfc3dc8 (diff)
alsa: optionally disable resampling and others
Added mpd.conf options for disabling automatic resamling, sample format and channel conversion. This way, users may choose to override ALSA's automatic resampling, and use libsamplerate instead.
-rw-r--r--doc/mpd.conf.513
-rw-r--r--src/audioOutputs/audioOutput_alsa.c16
2 files changed, 28 insertions, 1 deletions
diff --git a/doc/mpd.conf.5 b/doc/mpd.conf.5
index 5ede7e74..34c19408 100644
--- a/doc/mpd.conf.5
+++ b/doc/mpd.conf.5
@@ -274,6 +274,19 @@ Setting this allows you to use memory-mapped I/O. Certain hardware setups may
benefit from this, but most do not. Most users do not need to set this. The
default is to not use memory-mapped I/O.
.TP
+.B auto_resample <yes or no>
+Setting this to "no" disables ALSA's software resampling, if the
+hardware does not support a specific sample rate. This lets MPD do
+the resampling. "yes" is the default and allows ALSA to resample.
+.TP
+.B auto_channels <yes or no>
+Setting this to "no" disables ALSA's channel conversion, if the
+hardware does not support a specific number of channels. Default: "yes".
+.TP
+.B auto_format <yes or no>
+Setting this to "no" disables ALSA's sample format conversion, if the
+hardware does not support a specific sample format. Default: "yes".
+.TP
.B buffer_time <time in microseconds>
This sets the length of the hardware sample buffer in microseconds. Increasing
it may help to reduce or eliminate skipping on certain setups. Most users do
diff --git a/src/audioOutputs/audioOutput_alsa.c b/src/audioOutputs/audioOutput_alsa.c
index ebe40d04..e2132b9b 100644
--- a/src/audioOutputs/audioOutput_alsa.c
+++ b/src/audioOutputs/audioOutput_alsa.c
@@ -37,6 +37,10 @@ typedef snd_pcm_sframes_t alsa_writei_t(snd_pcm_t * pcm, const void *buffer,
typedef struct _AlsaData {
const char *device;
+
+ /** the mode flags passed to snd_pcm_open */
+ int mode;
+
snd_pcm_t *pcmHandle;
alsa_writei_t *writei;
unsigned int buffer_time;
@@ -50,6 +54,7 @@ static AlsaData *newAlsaData(void)
AlsaData *ret = xmalloc(sizeof(AlsaData));
ret->device = default_device;
+ ret->mode = 0;
ret->pcmHandle = NULL;
ret->writei = snd_pcm_writei;
ret->useMmap = 0;
@@ -80,6 +85,15 @@ alsa_configure(AlsaData *ad, ConfigParam *param)
ad->buffer_time = atoi(bp->value);
if ((bp = getBlockParam(param, "period_time")))
ad->period_time = atoi(bp->value);
+
+ if (!getBoolBlockParam(param, "auto_resample", true))
+ ad->mode |= SND_PCM_NO_AUTO_RESAMPLE;
+
+ if (!getBoolBlockParam(param, "auto_channels", true))
+ ad->mode |= SND_PCM_NO_AUTO_CHANNELS;
+
+ if (!getBoolBlockParam(param, "auto_format", true))
+ ad->mode |= SND_PCM_NO_AUTO_FORMAT;
}
static void *alsa_initDriver(mpd_unused struct audio_output *ao,
@@ -156,7 +170,7 @@ static int alsa_openDevice(void *data, struct audio_format *audioFormat)
ad->device, audioFormat->bits);
err = snd_pcm_open(&ad->pcmHandle, ad->device,
- SND_PCM_STREAM_PLAYBACK, 0);
+ SND_PCM_STREAM_PLAYBACK, ad->mode);
if (err < 0) {
ad->pcmHandle = NULL;
goto error;